summaryrefslogtreecommitdiffstats
path: root/src/usr/i2c
diff options
context:
space:
mode:
Diffstat (limited to 'src/usr/i2c')
-rwxr-xr-xsrc/usr/i2c/eepromdd.C452
-rwxr-xr-xsrc/usr/i2c/eepromdd.H17
-rwxr-xr-xsrc/usr/i2c/i2c.C426
-rwxr-xr-xsrc/usr/i2c/i2c.H144
-rwxr-xr-xsrc/usr/i2c/test/eepromddtest.H417
-rwxr-xr-xsrc/usr/i2c/test/i2ctest.H122
6 files changed, 973 insertions, 605 deletions
diff --git a/src/usr/i2c/eepromdd.C b/src/usr/i2c/eepromdd.C
index f734b66cc..8ea9b94c1 100755
--- a/src/usr/i2c/eepromdd.C
+++ b/src/usr/i2c/eepromdd.C
@@ -38,10 +38,10 @@
#include <trace/interface.H>
#include <errl/errlentry.H>
#include <errl/errlmanager.H>
+#include <errl/errludtarget.H>
#include <targeting/common/targetservice.H>
#include <devicefw/driverif.H>
#include <i2c/eepromddreasoncodes.H>
-
#include <i2c/eepromif.H>
#include "eepromdd.H"
@@ -90,6 +90,7 @@ DEVICE_REGISTER_ROUTE( DeviceFW::WILDCARD,
TARGETING::TYPE_MEMBUF,
eepromPerformOp );
+
// ------------------------------------------------------------------
// eepromPerformOp
// ------------------------------------------------------------------
@@ -103,7 +104,6 @@ errlHndl_t eepromPerformOp( DeviceFW::OperationType i_opType,
errlHndl_t err = NULL;
TARGETING::Target * theTarget = NULL;
eeprom_addr_t i2cInfo;
- i2cInfo.deviceType = LAST_DEVICE_TYPE;
i2cInfo.chip = va_arg( i_args, uint64_t );
i2cInfo.offset = va_arg( i_args, uint64_t );
@@ -138,6 +138,38 @@ errlHndl_t eepromPerformOp( DeviceFW::OperationType i_opType,
break;
}
+ // Check that the offset + data length is less than device max size
+ if ( ( i2cInfo.offset + io_buflen ) >
+ ( i2cInfo.devSize_KB * KILOBYTE ) )
+ {
+ TRACFCOMP( g_trac_eeprom,
+ ERR_MRK"eepromPerformOp(): Device Overflow! "
+ "C-p/e/dA=%d-%d/%d/0x%X, offset=0x%X, len=0x%X "
+ "devSizeKB=0x%X", i2cInfo.chip, i2cInfo.port,
+ i2cInfo.engine, i2cInfo.devAddr, i2cInfo.offset,
+ io_buflen, i2cInfo.devSize_KB);
+
+
+ /*@
+ * @errortype
+ * @reasoncode EEPROM_OVERFLOW_ERROR
+ * @severity ERRL_SEV_UNRECOVERABLE
+ * @moduleid EEPROM_PERFORM_OP
+ * @userdata1[0:31] Offset
+ * @userdata1[32:63] Buffer Length
+ * @userdata2 Device Max Size (in KB)
+ * @devdesc I2C Buffer Length + Offset > Max Size
+ */
+ err = new ERRORLOG::ErrlEntry( ERRORLOG::ERRL_SEV_UNRECOVERABLE,
+ EEPROM_PERFORM_OP,
+ EEPROM_OVERFLOW_ERROR,
+ TWO_UINT32_TO_UINT64(
+ i2cInfo.offset,
+ io_buflen ),
+ i2cInfo.devSize_KB );
+ break;
+ }
+
// Do the read or write
if( i_opType == DeviceFW::READ )
{
@@ -187,6 +219,13 @@ errlHndl_t eepromPerformOp( DeviceFW::OperationType i_opType,
}
} while( 0 );
+
+ // If there is an error, add target to log
+ if ( (err != NULL) && (i_target != NULL) )
+ {
+ ERRORLOG::ErrlUserDetailsTarget(i_target).addToLog(err);
+ }
+
TRACDCOMP( g_trac_eeprom,
EXIT_MRK"eepromPerformOp() - %s",
((NULL == err) ? "No Error" : "With Error") );
@@ -250,7 +289,7 @@ errlHndl_t eepromRead ( TARGETING::Target * i_target,
{
TRACFCOMP(g_trac_eeprom,
ERR_MRK"eepromRead(): I2C Read-Offset failed on "
- "%d/%d/0x%x",
+ "%d/%d/0x%X",
i_i2cInfo.port, i_i2cInfo.engine, i_i2cInfo.devAddr);
break;
}
@@ -269,7 +308,7 @@ errlHndl_t eepromRead ( TARGETING::Target * i_target,
if( err )
{
TRACFCOMP(g_trac_eeprom,
- ERR_MRK"eepromRead(): I2C Read failed on %d/%d/0x%x",
+ ERR_MRK"eepromRead(): I2C Read failed on %d/%d/0x%0X",
i_i2cInfo.port, i_i2cInfo.engine, i_i2cInfo.devAddr);
break;
}
@@ -312,7 +351,6 @@ errlHndl_t eepromWrite ( TARGETING::Target * i_target,
uint8_t * newBuffer = NULL;
bool needFree = false;
bool unlock = false;
- eeprom_addr_t l_i2cInfo = i_i2cInfo;
TRACDCOMP( g_trac_eeprom,
ENTER_MRK"eepromWrite()" );
@@ -337,8 +375,8 @@ errlHndl_t eepromWrite ( TARGETING::Target * i_target,
// EEPROM devices have write page boundaries, so when necessary
// need to split up command into multiple write operations
- // Setup a max-size buffer of byteAddrSize + writePageSize
- size_t newBufLen = byteAddrSize + i_i2cInfo.writePageSize;
+ // Setup a max-size buffer of writePageSize
+ size_t newBufLen = i_i2cInfo.writePageSize;
newBuffer = static_cast<uint8_t*>(malloc( newBufLen ));
needFree = true;
@@ -351,7 +389,6 @@ errlHndl_t eepromWrite ( TARGETING::Target * i_target,
// variables to store different amount of data length
size_t loop_data_length = 0;
- size_t loop_buffer_length = 0;
size_t total_bytes_written = 0;
for ( uint64_t i = 0 ;
@@ -372,55 +409,56 @@ errlHndl_t eepromWrite ( TARGETING::Target * i_target,
loop_data_length = io_buflen % i_i2cInfo.writePageSize;
}
- // Update the offset for each loop
- l_i2cInfo.offset += i * i_i2cInfo.writePageSize;
+ // Add the data the user wanted to write
+ memcpy( newBuffer,
+ &l_data_ptr[i * i_i2cInfo.writePageSize],
+ loop_data_length);
+
- err = eepromPrepareAddress( &byteAddr,
- byteAddrSize,
- l_i2cInfo );
- if (err)
+ // Update the offset for each loop after the first one
+ if ( i > 0 )
{
- break;
+ i_i2cInfo.offset += i_i2cInfo.writePageSize;
}
- // Add the byte address to the buffer
- memcpy( newBuffer,
- byteAddr,
- byteAddrSize );
+ // Setup offset/address parms
+ err = eepromPrepareAddress( &byteAddr,
+ byteAddrSize,
+ i_i2cInfo );
- // Now add the data the user wanted to write
- memcpy( &newBuffer[byteAddrSize],
- &l_data_ptr[i * i_i2cInfo.writePageSize],
- loop_data_length);
+ if( err )
+ {
+ break;
+ }
- // Calculate Total Length
- loop_buffer_length = loop_data_length + byteAddrSize;
- TRACUCOMP(g_trac_eeprom,"eepromWrite() Loop: %d/%d/0x%x "
- "loop=%d, l_b_l=%d, l_d_l=%d, offset=0x%x",
- i_i2cInfo.port, i_i2cInfo.engine,
- i_i2cInfo.devAddr, i, loop_buffer_length, loop_data_length,
- l_i2cInfo.offset);
+ TRACUCOMP(g_trac_eeprom,"eepromWrite() Loop: %d/%d/0x%X "
+ "loop=%d, l_d_l=%d, offset=0x%X, bAS=%d",
+ i_i2cInfo.port, i_i2cInfo.engine, i_i2cInfo.devAddr,
+ i, loop_data_length, i_i2cInfo.offset, byteAddrSize);
// Do the actual data write
err = deviceOp( DeviceFW::WRITE,
i_target,
newBuffer,
- loop_buffer_length,
- DEVICE_I2C_ADDRESS( i_i2cInfo.port,
- i_i2cInfo.engine,
- i_i2cInfo.devAddr ) );
+ loop_data_length,
+ DEVICE_I2C_ADDRESS_OFFSET(
+ i_i2cInfo.port,
+ i_i2cInfo.engine,
+ i_i2cInfo.devAddr,
+ byteAddrSize,
+ reinterpret_cast<uint8_t*>(
+ &byteAddr)));
if( err )
{
TRACFCOMP(g_trac_eeprom,
- ERR_MRK"eepromWrite(): I2C Write failed on %d/%d/0x%x "
- "loop=%d, l_b_l=%d, offset=0x%x",
- i_i2cInfo.port, i_i2cInfo.engine,
- i_i2cInfo.devAddr, i, loop_buffer_length, l_i2cInfo.offset);
-
+ ERR_MRK"eepromWrite(): I2C Write failed on %d/%d/0x%X "
+ "loop=%d, l_d_l=%d, offset=0x%X, aS=%d",
+ i_i2cInfo.port, i_i2cInfo.engine, i_i2cInfo.devAddr, i,
+ loop_data_length, i_i2cInfo.offset, i_i2cInfo.addrSize);
// Can't assume that anything was written if
// there was an error, so no update to total_bytes_written
@@ -430,7 +468,8 @@ errlHndl_t eepromWrite ( TARGETING::Target * i_target,
// Update how much data was written
total_bytes_written += loop_data_length;
- }
+
+ } // end of write for-loop
// Release mutex lock
mutex_unlock( &g_eepromMutex );
@@ -473,7 +512,7 @@ errlHndl_t eepromWrite ( TARGETING::Target * i_target,
// ------------------------------------------------------------------
// eepromPrepareAddress
// ------------------------------------------------------------------
-errlHndl_t eepromPrepareAddress ( void * o_buffer,
+errlHndl_t eepromPrepareAddress ( void * io_buffer,
size_t & o_bufSize,
eeprom_addr_t i_i2cInfo )
{
@@ -486,57 +525,53 @@ errlHndl_t eepromPrepareAddress ( void * o_buffer,
do
{
+
// --------------------------------------------------------------------
- // @todo RTC:72715 - support different I2C devices and the way
- // they handle addressing. A new attribute will need to be added to
- // EEPROM_ADDR_INFOx to indicate the device type so the addressing
- // here can be handled properly.
- //
- // Until we get a different device, we'll just code for the 2 examples
- // that I know of now.
+ // Currently only supporting I2C devices and that use 0, 1, or 2 bytes
+ // to set the offset (ie, internal address) into the device.
// --------------------------------------------------------------------
- switch( i_i2cInfo.deviceType )
+ switch( i_i2cInfo.addrSize )
{
case TWO_BYTE_ADDR:
o_bufSize = 2;
- memset( o_buffer, 0x0, o_bufSize );
- *((uint8_t*)o_buffer) = (i_i2cInfo.offset & 0xFF00ull) >> 8;
- *((uint8_t*)o_buffer+1) = (i_i2cInfo.offset & 0x00FFull);
+ memset( io_buffer, 0x0, o_bufSize );
+ *((uint8_t*)io_buffer) = (i_i2cInfo.offset & 0xFF00ull) >> 8;
+ *((uint8_t*)io_buffer+1) = (i_i2cInfo.offset & 0x00FFull);
break;
case ONE_BYTE_ADDR:
o_bufSize = 1;
- memset( o_buffer, 0x0, o_bufSize );
- *((uint8_t*)o_buffer) = (i_i2cInfo.offset & 0xFFull);
+ memset( io_buffer, 0x0, o_bufSize );
+ *((uint8_t*)io_buffer) = (i_i2cInfo.offset & 0xFFull);
+ break;
+
+ case ZERO_BYTE_ADDR:
+ o_bufSize = 0;
+ // nothing to do with the buffer in this case
break;
default:
TRACFCOMP( g_trac_eeprom,
- ERR_MRK"eepromPrepareAddress() - Invalid device type: %08x",
- i_i2cInfo.deviceType );
+ ERR_MRK"eepromPrepareAddress() - Invalid Device "
+ "Address Size: 0x%08x", i_i2cInfo.addrSize);
/*@
* @errortype
* @reasoncode EEPROM_INVALID_DEVICE_TYPE
* @severity ERRL_SEV_UNRECOVERABLE
* @moduleid EEPROM_PREPAREADDRESS
- * @userdata1 Device Type
+ * @userdata1 Address Size (aka Device Type)
* @userdata2 EEPROM chip
- * @devdesc The Device type was not recognized as one supported.
+ * @devdesc The Device type not supported (addrSize)
*/
err = new ERRORLOG::ErrlEntry( ERRORLOG::ERRL_SEV_UNRECOVERABLE,
EEPROM_PREPAREADDRESS,
EEPROM_INVALID_DEVICE_TYPE,
- i_i2cInfo.deviceType,
- i_i2cInfo.chip );
-
+ i_i2cInfo.addrSize,
+ i_i2cInfo.chip);
break;
- };
-
- if( err )
- {
- break;
}
+
} while( 0 );
TRACDCOMP( g_trac_eeprom,
@@ -553,227 +588,174 @@ errlHndl_t eepromReadAttributes ( TARGETING::Target * i_target,
eeprom_addr_t & o_i2cInfo )
{
errlHndl_t err = NULL;
+ bool fail_reading_attribute = false;
TRACDCOMP( g_trac_eeprom,
ENTER_MRK"eepromReadAttributes()" );
+ // These variables will be used to hold the EEPROM attribute data
+ // Note: each 'EepromVpd' struct is kept the same via the attributes
+ // so will be copying each to eepromData to save code space
+ TARGETING::EepromVpdPrimaryInfo eepromData;
+
do
{
- if( VPD_PRIMARY == o_i2cInfo.chip )
+
+ switch (o_i2cInfo.chip )
{
- // Read Attributes from EEPROM_VPD_PRIMARY_INFO
- TARGETING::EepromVpdPrimaryInfo eepromData;
- if( i_target->tryGetAttr<TARGETING::ATTR_EEPROM_VPD_PRIMARY_INFO>
- ( eepromData ) )
- {
- o_i2cInfo.chipTypeEnum = VPD_PRIMARY;
- o_i2cInfo.port = eepromData.port;
- o_i2cInfo.devAddr = eepromData.devAddr;
- o_i2cInfo.engine = eepromData.engine;
- o_i2cInfo.i2cMasterPath = eepromData.i2cMasterPath;
+ case VPD_PRIMARY:
+ if( !( i_target->
+ tryGetAttr<TARGETING::ATTR_EEPROM_VPD_PRIMARY_INFO>
+ ( eepromData ) ) )
+
+ {
+ fail_reading_attribute = true;
+ }
+ break;
- // @todo RTC:72715 - More attributes to be read
- o_i2cInfo.deviceType = TWO_BYTE_ADDR;
- o_i2cInfo.writePageSize = 128;
+ case VPD_BACKUP:
- }
- else
- {
- TRACFCOMP( g_trac_eeprom,
- ERR_MRK"eepromReadAttributes() - ERROR reading "
- "attributes for chip %d! (VPD_PRIMARY)",
- o_i2cInfo.chip );
+ if( !(i_target->
+ tryGetAttr<TARGETING::ATTR_EEPROM_VPD_BACKUP_INFO>
+ ( reinterpret_cast<
+ TARGETING::ATTR_EEPROM_VPD_BACKUP_INFO_type&>
+ ( eepromData) ) ) )
+ {
+ fail_reading_attribute = true;
+ }
+ break;
- /*@
- * @errortype
- * @reasoncode EEPROM_VPD_PRIMARY_INFO_NOT_FOUND
- * @severity ERRORLOG::ERRL_SEV_UNRECOVERABLE
- * @moduleid EEPROM_READATTRIBUTES
- * @userdata1 HUID of target
- * @userdata2[0:31] EEPROM chip
- * @userdata2[32:63] Attribute Enumeration
- * @devdesc ATTR_EEPROM_VPD_PRIMARY_INFO Attribute
- * was not found
- */
- err = new ERRORLOG::ErrlEntry(
- ERRORLOG::ERRL_SEV_UNRECOVERABLE,
- EEPROM_READATTRIBUTES,
- EEPROM_VPD_PRIMARY_INFO_NOT_FOUND,
- TARGETING::get_huid(i_target),
- TWO_UINT32_TO_UINT64(
- o_i2cInfo.chip,
- TARGETING::ATTR_EEPROM_VPD_PRIMARY_INFO));
+ case SBE_PRIMARY:
+ if( !(i_target->
+ tryGetAttr<TARGETING::ATTR_EEPROM_SBE_PRIMARY_INFO>
+ ( reinterpret_cast<
+ TARGETING::ATTR_EEPROM_SBE_PRIMARY_INFO_type&>
+ ( eepromData) ) ) )
+ {
+ fail_reading_attribute = true;
+ }
+ break;
+
+ case SBE_BACKUP:
+ if( (!i_target->
+ tryGetAttr<TARGETING::ATTR_EEPROM_SBE_BACKUP_INFO>
+ ( reinterpret_cast<
+ TARGETING::ATTR_EEPROM_SBE_BACKUP_INFO_type&>
+ ( eepromData) ) ) )
+ {
+ fail_reading_attribute = true;
+ }
break;
- }
- }
- else if( VPD_BACKUP == o_i2cInfo.chip )
- {
- // Read Attributes from EEPROM_VPD_BACKUP_INFO
- TARGETING::EepromVpdBackupInfo eepromData;
- if( i_target->tryGetAttr<TARGETING::ATTR_EEPROM_VPD_BACKUP_INFO>
- ( eepromData ) )
- {
- o_i2cInfo.chipTypeEnum = VPD_BACKUP;
- o_i2cInfo.port = eepromData.port;
- o_i2cInfo.devAddr = eepromData.devAddr;
- o_i2cInfo.engine = eepromData.engine;
- o_i2cInfo.i2cMasterPath = eepromData.i2cMasterPath;
-
- // @todo RTC:72715 - More attributes to be read
- o_i2cInfo.deviceType = TWO_BYTE_ADDR;
- o_i2cInfo.writePageSize = 128;
- }
- else
- {
- TRACFCOMP( g_trac_eeprom,
- ERR_MRK"eepromReadAttributes() - ERROR reading "
- "attributes for chip %d! (VPD_BACKUP)",
- o_i2cInfo.chip );
+
+ default:
+ TRACFCOMP( g_trac_eeprom,ERR_MRK"eepromReadAttributes() - "
+ "Invalid chip (%d) to read attributes from!",
+ o_i2cInfo.chip );
/*@
* @errortype
- * @reasoncode EEPROM_VPD_BACKUP_INFO_NOT_FOUND
+ * @reasoncode EEPROM_INVALID_CHIP
* @severity ERRORLOG::ERRL_SEV_UNRECOVERABLE
* @moduleid EEPROM_READATTRIBUTES
- * @userdata1 HUID of target
- * @userdata2[0:31] EEPROM chip
- * @userdata2[32:63] Attribute Enumeration
- * @devdesc ATTR_EEPROM_VPD_BACKUP_INFO Attribute
- * was not found
+ * @userdata1 EEPROM Chip
+ * @userdata2 HUID of target
+ * @devdesc Invalid EEPROM chip to access
*/
- err = new ERRORLOG::ErrlEntry(
- ERRORLOG::ERRL_SEV_UNRECOVERABLE,
- EEPROM_READATTRIBUTES,
- EEPROM_VPD_BACKUP_INFO_NOT_FOUND,
- TARGETING::get_huid(i_target),
- TWO_UINT32_TO_UINT64(
- o_i2cInfo.chip,
- TARGETING::ATTR_EEPROM_VPD_PRIMARY_INFO));
+ err = new ERRORLOG::ErrlEntry(ERRORLOG::ERRL_SEV_UNRECOVERABLE,
+ EEPROM_READATTRIBUTES,
+ EEPROM_INVALID_CHIP,
+ o_i2cInfo.chip,
+ TARGETING::get_huid(i_target) );
break;
- }
}
- else if( SBE_PRIMARY == o_i2cInfo.chip )
+
+ // Check if Attribute Data was found
+ if( fail_reading_attribute == true )
{
- // Read Attributes from EEPROM_SBE_PRIMARY_INFO
- TARGETING::EepromSbePrimaryInfo eepromData;
- if( i_target->tryGetAttr<TARGETING::ATTR_EEPROM_SBE_PRIMARY_INFO>
- ( eepromData ) )
- {
- o_i2cInfo.chipTypeEnum = SBE_PRIMARY;
- o_i2cInfo.port = eepromData.port;
- o_i2cInfo.devAddr = eepromData.devAddr;
- o_i2cInfo.engine = eepromData.engine;
- o_i2cInfo.i2cMasterPath = eepromData.i2cMasterPath;
-
- // @todo RTC:72715 - More attributes to be read
- o_i2cInfo.deviceType = TWO_BYTE_ADDR;
- o_i2cInfo.writePageSize = 128;
- }
- else
- {
- TRACFCOMP( g_trac_eeprom,
- ERR_MRK"eepromReadAttributes() - ERROR reading "
- "attributes for chip %d! (SBE_PRIMARY)",
- o_i2cInfo.chip );
+ TRACFCOMP( g_trac_eeprom,
+ ERR_MRK"eepromReadAttributes() - ERROR reading "
+ "attributes for chip %d!",
+ o_i2cInfo.chip );
/*@
* @errortype
- * @reasoncode EEPROM_SBE_PRIMARY_INFO_NOT_FOUND
+ * @reasoncode EEPROM_ATTR_INFO_NOT_FOUND
* @severity ERRORLOG::ERRL_SEV_UNRECOVERABLE
* @moduleid EEPROM_READATTRIBUTES
* @userdata1 HUID of target
- * @userdata2[0:31] EEPROM chip
- * @userdata2[32:63] Attribute Enumeration
- * @devdesc ATTR_EEPROM_SBE_PRIMARY_INFO Attribute
- * was not found
+ * @userdata2 EEPROM chip
+ * @devdesc EEPROM Attribute was not found
*/
err = new ERRORLOG::ErrlEntry(
ERRORLOG::ERRL_SEV_UNRECOVERABLE,
EEPROM_READATTRIBUTES,
- EEPROM_SBE_PRIMARY_INFO_NOT_FOUND,
+ EEPROM_ATTR_INFO_NOT_FOUND,
TARGETING::get_huid(i_target),
- TWO_UINT32_TO_UINT64(
- o_i2cInfo.chip,
- TARGETING::ATTR_EEPROM_VPD_PRIMARY_INFO));
+ o_i2cInfo.chip);
break;
- }
+
+ }
+
+ // Successful reading of Attribute, so extract the data
+ o_i2cInfo.port = eepromData.port;
+ o_i2cInfo.devAddr = eepromData.devAddr;
+ o_i2cInfo.engine = eepromData.engine;
+ o_i2cInfo.i2cMasterPath = eepromData.i2cMasterPath;
+ o_i2cInfo.writePageSize = eepromData.writePageSize;
+ o_i2cInfo.devSize_KB = eepromData.maxMemorySizeKB;
+
+ // Convert attribute info to eeprom_addr_size_t enum
+ if ( eepromData.byteAddrOffset == 0x2 )
+ {
+ o_i2cInfo.addrSize = TWO_BYTE_ADDR;
}
- else if( SBE_BACKUP == o_i2cInfo.chip )
+ else if ( eepromData.byteAddrOffset == 0x1 )
{
- // Read Attributes from EEPROM_SBE_BACKUP_INFO
- TARGETING::EepromSbeBackupInfo eepromData;
- if( i_target->tryGetAttr<TARGETING::ATTR_EEPROM_SBE_BACKUP_INFO>
- ( eepromData ) )
- {
- o_i2cInfo.chipTypeEnum = SBE_BACKUP;
- o_i2cInfo.port = eepromData.port;
- o_i2cInfo.devAddr = eepromData.devAddr;
- o_i2cInfo.engine = eepromData.engine;
- o_i2cInfo.i2cMasterPath = eepromData.i2cMasterPath;
-
- // @todo RTC:72715 - More attributes to be read
- o_i2cInfo.deviceType = TWO_BYTE_ADDR;
- o_i2cInfo.writePageSize = 128;
- }
- else
- {
- TRACFCOMP( g_trac_eeprom,
- ERR_MRK"eepromReadAttributes() - ERROR reading "
- "attributes for chip %d! (SBE_BACKUP)",
- o_i2cInfo.chip );
+ o_i2cInfo.addrSize = ONE_BYTE_ADDR;
+ }
+ else if ( eepromData.byteAddrOffset == 0x0 )
+ {
+ o_i2cInfo.addrSize = ZERO_BYTE_ADDR;
+ }
+ else
+ {
+ TRACFCOMP( g_trac_eeprom,
+ ERR_MRK"eepromReadAttributes() - INVALID ADDRESS "
+ "OFFSET SIZE %d!",
+ o_i2cInfo.addrSize );
/*@
* @errortype
- * @reasoncode EEPROM_SBE_BACKUP_INFO_NOT_FOUND
+ * @reasoncode EEPROM_INVALID_ADDR_OFFSET_SIZE
* @severity ERRORLOG::ERRL_SEV_UNRECOVERABLE
* @moduleid EEPROM_READATTRIBUTES
* @userdata1 HUID of target
- * @userdata2[0:31] EEPROM chip
- * @userdata2[32:63] Attribute Enumeration
- * @devdesc ATTR_EEPROM_SBE_BACKUP_INFO Attribute
- * was not found
+ * @userdata2 Address Offset Size
+ * @devdesc Invalid Address Offset Size
*/
err = new ERRORLOG::ErrlEntry(
ERRORLOG::ERRL_SEV_UNRECOVERABLE,
EEPROM_READATTRIBUTES,
- EEPROM_SBE_BACKUP_INFO_NOT_FOUND,
+ EEPROM_INVALID_ADDR_OFFSET_SIZE,
TARGETING::get_huid(i_target),
- TWO_UINT32_TO_UINT64(
- o_i2cInfo.chip,
- TARGETING::ATTR_EEPROM_VPD_PRIMARY_INFO));
+ o_i2cInfo.addrSize);
break;
- }
- }
- else
- {
- TRACFCOMP( g_trac_eeprom,
- ERR_MRK"eepromReadAttributes() - Invalid chip (%d) to read "
- "attributes from!",
- o_i2cInfo.chip );
-
- /*@
- * @errortype
- * @reasoncode EEPROM_INVALID_CHIP
- * @severity ERRORLOG::ERRL_SEV_UNRECOVERABLE
- * @moduleid EEPROM_READATTRIBUTES
- * @userdata1 EEPROM Chip
- * @userdata2 HUID of target
- * @devdesc Invalid EEPROM chip to access
- */
- err = new ERRORLOG::ErrlEntry( ERRORLOG::ERRL_SEV_UNRECOVERABLE,
- EEPROM_READATTRIBUTES,
- EEPROM_INVALID_CHIP,
- o_i2cInfo.chip,
- TARGETING::get_huid(i_target) );
- break;
}
+
} while( 0 );
+ TRACUCOMP(g_trac_eeprom,"eepromReadAttributes() %d/%d/0x%X "
+ "wpw=0x%X, dsKb=0x%X, aS=%d (%d)",
+ o_i2cInfo.port, o_i2cInfo.engine, o_i2cInfo.devAddr,
+ o_i2cInfo.writePageSize, o_i2cInfo.devSize_KB,
+ o_i2cInfo.addrSize, eepromData.byteAddrOffset);
+
+
TRACDCOMP( g_trac_eeprom,
EXIT_MRK"eepromReadAttributes()" );
@@ -831,7 +813,7 @@ errlHndl_t eepromGetI2CMasterTarget ( TARGETING::Target * i_target,
ERRORLOG::ERRL_SEV_UNRECOVERABLE,
EEPROM_GETI2CMASTERTARGET,
EEPROM_DIMM_I2C_MASTER_PATH_ERROR,
- i_i2cInfo.chipTypeEnum,
+ i_i2cInfo.chip,
TARGETING::get_huid(i_target) );
break;
@@ -858,7 +840,7 @@ errlHndl_t eepromGetI2CMasterTarget ( TARGETING::Target * i_target,
err = new ERRORLOG::ErrlEntry( ERRORLOG::ERRL_SEV_UNRECOVERABLE,
EEPROM_GETI2CMASTERTARGET,
EEPROM_TARGET_NULL,
- i_i2cInfo.chipTypeEnum,
+ i_i2cInfo.chip,
TARGETING::get_huid(i_target) );
break;
diff --git a/src/usr/i2c/eepromdd.H b/src/usr/i2c/eepromdd.H
index 7464e1881..d30862b62 100755
--- a/src/usr/i2c/eepromdd.H
+++ b/src/usr/i2c/eepromdd.H
@@ -44,10 +44,11 @@ namespace EEPROM
*/
typedef enum
{
- TWO_BYTE_ADDR,
- ONE_BYTE_ADDR,
+ ZERO_BYTE_ADDR = 0,
+ ONE_BYTE_ADDR = 1,
+ TWO_BYTE_ADDR = 2,
LAST_DEVICE_TYPE
-} eeprom_device_t;
+} eeprom_addr_size_t;
/**
* @brief Structure of common parameters needed by different parts of
@@ -60,10 +61,10 @@ typedef struct
uint64_t devAddr;
int64_t chip;
uint64_t offset;
- eeprom_device_t deviceType;
+ eeprom_addr_size_t addrSize;
TARGETING::EntityPath i2cMasterPath;
uint64_t writePageSize; // in bytes
- eeprom_chip_types_t chipTypeEnum;
+ uint64_t devSize_KB; // in kilobytes
} eeprom_addr_t;
/**
@@ -156,8 +157,8 @@ errlHndl_t eepromWrite ( TARGETING::Target * i_target,
* existing buffer (for Writes), or as a separate write operation
* (for Reads).
*
- * @param[out] o_buffer - The buffer to be written as a byte address to
- * the EEPROM device.
+ * @param[in/out] io_buffer - The buffer to be written as a byte address to
+ * the EEPROM device. Must be pre-allocated to MAX_BYTE_ADDR size.
*
* @param[out] o_bufSize - The size of the buffer to be written.
*
@@ -167,7 +168,7 @@ errlHndl_t eepromWrite ( TARGETING::Target * i_target,
* @return errlHndl_t - NULL if successful, otherwise a pointer to the
* error log.
*/
-errlHndl_t eepromPrepareAddress ( void * o_buffer,
+errlHndl_t eepromPrepareAddress ( void * io_buffer,
size_t & o_bufSize,
eeprom_addr_t i_i2cInfo );
diff --git a/src/usr/i2c/i2c.C b/src/usr/i2c/i2c.C
index 66d39bc6e..19403c9b4 100755
--- a/src/usr/i2c/i2c.C
+++ b/src/usr/i2c/i2c.C
@@ -36,6 +36,7 @@
#include <trace/interface.H>
#include <errl/errlentry.H>
#include <errl/errlmanager.H>
+#include <errl/errludtarget.H>
#include <targeting/common/targetservice.H>
#include <devicefw/driverif.H>
#include <targeting/common/predicates/predicates.H>
@@ -97,12 +98,14 @@ errlHndl_t i2cPerformOp( DeviceFW::OperationType i_opType,
va_list i_args )
{
errlHndl_t err = NULL;
- bool l_withStop = false;
- bool l_skipModeSetup = false;
+
+ mutex_t * engineLock = NULL;
+ bool mutex_needs_unlock = false;
// Get the input args our of the va_list
// Address, Port, Engine, Device Addr.
- input_args_t args;
+ // Other args set below
+ misc_args_t args;
args.port = va_arg( i_args, uint64_t );
args.engine = va_arg( i_args, uint64_t );
args.devAddr = va_arg( i_args, uint64_t );
@@ -132,6 +135,7 @@ errlHndl_t i2cPerformOp( DeviceFW::OperationType i_opType,
(uint64_t) i_opType, i_accessType, args.port, args.engine,
args.devAddr, io_buflen, l_offset_length, l_offset_buffer);
+
do
{
// Check for Master Sentinel chip
@@ -160,10 +164,8 @@ errlHndl_t i2cPerformOp( DeviceFW::OperationType i_opType,
break;
}
- // @todo RTC:72715 - Check that target is an I2C master
// Get the mutex for the requested engine
- mutex_t * engineLock = NULL;
switch( args.engine )
{
case 0:
@@ -191,10 +193,21 @@ errlHndl_t i2cPerformOp( DeviceFW::OperationType i_opType,
INFO_MRK"Obtaining lock for engine: %d",
args.engine );
(void)mutex_lock( engineLock );
+ mutex_needs_unlock = true;
TRACUCOMP( g_trac_i2c,
INFO_MRK"Locked on engine: %d",
args.engine );
+
+ // Calculate variables related to I2C Bus Speed in 'args' struct
+ err = i2cSetBusVariables( i_target, READ_I2C_BUS_ATTRIBUTES, args);
+
+ if( err )
+ {
+ break;
+ }
+
+
for( int attempt = 0; attempt < I2C_COMMAND_ATTEMPTS; attempt++ )
{
if( err )
@@ -227,25 +240,30 @@ errlHndl_t i2cPerformOp( DeviceFW::OperationType i_opType,
{
// First WRITE offset to device without a stop
- l_withStop = false;
+ args.read_not_write = false;
+ args.with_stop = false;
+ args.skip_mode_setup = false;
err = i2cWrite( i_target,
l_offset_buffer,
l_offset_length,
- l_withStop,
args );
-
-
- // Now do the READ with a stop (reads always have 'stop')
- // Skip mode setup on this cmd - already set with previous cmd
- l_skipModeSetup = true;
-
- err = i2cRead( i_target,
- io_buffer,
- io_buflen,
- l_skipModeSetup,
- args );
+ if( err == NULL )
+ {
+ // Now do the READ with a stop
+ args.read_not_write = true;
+ args.with_stop = true;
+
+ // Skip mode setup on this cmd -
+ // already set with previous cmd
+ args.skip_mode_setup = true;
+
+ err = i2cRead( i_target,
+ io_buffer,
+ io_buflen,
+ args );
+ }
}
else if( i_opType == DeviceFW::WRITE &&
@@ -264,14 +282,14 @@ errlHndl_t i2cPerformOp( DeviceFW::OperationType i_opType,
// Now add the data the user wanted to write
memcpy( &newBuffer[l_offset_length], io_buffer, io_buflen);
- // Other parms:
- l_withStop = true;
- l_skipModeSetup = false;
+ // Write parms:
+ args.read_not_write = false;
+ args.with_stop = true;
+ args.skip_mode_setup = false;
err = i2cWrite( i_target,
newBuffer,
newBufLen,
- l_withStop,
args );
@@ -283,13 +301,14 @@ errlHndl_t i2cPerformOp( DeviceFW::OperationType i_opType,
l_offset_length == 0 )
{
// Do a direct READ
- l_skipModeSetup = false;
+ args.read_not_write = true;
+ args.with_stop = true;
+ args.skip_mode_setup = false;
err = i2cRead( i_target,
io_buffer,
io_buflen,
- l_skipModeSetup,
- args );
+ args);
}
@@ -297,12 +316,14 @@ errlHndl_t i2cPerformOp( DeviceFW::OperationType i_opType,
l_offset_length == 0 )
{
// Do a direct WRITE with a stop
- l_withStop = true;
+ args.read_not_write = false;
+ args.with_stop = true;
+ args.skip_mode_setup = false;
+
err = i2cWrite( i_target,
io_buffer,
io_buflen,
- l_withStop,
- args );
+ args);
}
else
{
@@ -342,17 +363,27 @@ errlHndl_t i2cPerformOp( DeviceFW::OperationType i_opType,
}
}
+ if( err )
+ {
+ break;
+ }
+ } while( 0 );
+
+ // Check if we need to unlock the mutex
+ if ( mutex_needs_unlock == true )
+ {
// Unlock
(void) mutex_unlock( engineLock );
TRACUCOMP( g_trac_i2c,
INFO_MRK"Unlocked engine: %d",
args.engine );
+ }
- if( err )
- {
- break;
- }
- } while( 0 );
+ // If there is an error, add target to log
+ if ( (err != NULL) && (i_target != NULL) )
+ {
+ ERRORLOG::ErrlUserDetailsTarget(i_target).addToLog(err);
+ }
TRACDCOMP( g_trac_i2c,
EXIT_MRK"i2cPerformOp() - %s",
@@ -367,40 +398,35 @@ errlHndl_t i2cPerformOp( DeviceFW::OperationType i_opType,
errlHndl_t i2cRead ( TARGETING::Target * i_target,
void * o_buffer,
size_t & i_buflen,
- bool & i_skipModeSetup,
- input_args_t i_args )
+ misc_args_t & i_args)
{
errlHndl_t err = NULL;
- size_t size = sizeof(uint64_t);
uint64_t bytesRead = 0x0;
+ size_t size = sizeof(uint64_t);
- uint64_t engine = i_args.engine;
- uint64_t devAddr = i_args.devAddr;
- uint64_t port = i_args.port;
- // @todo RTC:72715 - Add multiple bus speed support (set to 400KHz for now)
- uint64_t interval = I2C_TIMEOUT_INTERVAL( I2C_CLOCK_DIVISOR_400KHZ );
- uint64_t timeoutCount = I2C_TIMEOUT_COUNT( interval );
+ // Use Local Variables (timeoutCount gets derecmented)
+ uint64_t interval = i_args.timeout_interval;
+ uint64_t timeoutCount = i_args.timeout_count;
// Define the regs we'll be using
- statusreg status;
- fiforeg fifo;
+ status_reg_t status;
+ fifo_reg_t fifo;
TRACDCOMP( g_trac_i2c,
ENTER_MRK"i2cRead()" );
TRACSCOMP( g_trac_i2cr,
"I2C READ START : engine %.2X : port %.2X : devAddr %.2X : len %d",
- engine, port, devAddr, i_buflen );
+ i_args.engine, i_args.port, i_args.devAddr, i_buflen );
do
{
// Do Command/Mode reg setups.
+ i_args.read_not_write = true;
+
err = i2cSetup( i_target,
i_buflen,
- true, // i_readNotWrite
- true, // i_withStop
- i_skipModeSetup,
i_args );
if( err )
@@ -455,8 +481,8 @@ errlHndl_t i2cRead ( TARGETING::Target * i_target,
ERR_MRK"i2cRead() - Timed out waiting for data in FIFO!" );
uint64_t userdata2 = i_args.port;
- userdata2 = (userdata2 << 16) | engine;
- userdata2 = (userdata2 << 16) | devAddr;
+ userdata2 = (userdata2 << 16) | i_args.engine;
+ userdata2 = (userdata2 << 16) | i_args.devAddr;
/*@
* @errortype
@@ -464,8 +490,7 @@ errlHndl_t i2cRead ( TARGETING::Target * i_target,
* @severity ERRL_SEV_UNRECOVERABLE
* @moduleid I2C_READ
* @userdata1 Status Register Value
- * @userdata2[0:15] <UNUSED>
- * @userdata2[16:31] Master Port
+ * @userdata2[0:31] Master Port
* @userdata2[32:47] Master Engine
* @userdata2[48:63] Slave Device Address
* @devdesc Timed out waiting for data in FIFO to read
@@ -490,11 +515,12 @@ errlHndl_t i2cRead ( TARGETING::Target * i_target,
err = deviceRead( i_target,
&fifo.value,
size,
- DEVICE_SCOM_ADDRESS( masterAddrs[engine].fifo ) );
+ DEVICE_SCOM_ADDRESS(
+ masterAddrs[i_args.engine].fifo ) );
TRACUCOMP( g_trac_i2c,
INFO_MRK"i2cRead() - FIFO[0x%lx] = 0x%016llx",
- masterAddrs[engine].fifo, fifo.value);
+ masterAddrs[i_args.engine].fifo, fifo.value);
if( err )
{
@@ -509,7 +535,7 @@ errlHndl_t i2cRead ( TARGETING::Target * i_target,
TRACUCOMP( g_trac_i2cr,
"I2C READ DATA : engine %.2X : port %.2x : "
"devAddr %.2X : byte %d : %.2X (0x%lx)",
- engine, port, devAddr, bytesRead,
+ i_args.engine, i_args.port, i_args.devAddr, bytesRead,
fifo.byte_0, fifo.value );
}
@@ -530,7 +556,7 @@ errlHndl_t i2cRead ( TARGETING::Target * i_target,
TRACSCOMP( g_trac_i2cr,
"I2C READ END : engine %.2X : port %.2x : devAddr %.2X : len %d",
- engine, port, devAddr, i_buflen );
+ i_args.engine, i_args.port, i_args.devAddr, i_buflen );
TRACDCOMP( g_trac_i2c,
EXIT_MRK"i2cRead()" );
@@ -544,36 +570,30 @@ errlHndl_t i2cRead ( TARGETING::Target * i_target,
errlHndl_t i2cWrite ( TARGETING::Target * i_target,
void * i_buffer,
size_t & io_buflen,
- bool & i_withStop,
- input_args_t i_args )
+ misc_args_t & i_args)
{
errlHndl_t err = NULL;
- size_t size = sizeof(uint64_t);
uint64_t bytesWritten = 0x0;
-
- uint64_t engine = i_args.engine;
- uint64_t devAddr = i_args.devAddr;
- uint64_t port = i_args.port;
+ size_t size = sizeof(uint64_t);
// Define regs we'll be using
- fiforeg fifo;
+ fifo_reg_t fifo;
TRACDCOMP( g_trac_i2c,
ENTER_MRK"i2cWrite()" );
TRACSCOMP( g_trac_i2cr,
"I2C WRITE START : engine %.2X : port %.2X : devAddr %.2X : len %d",
- engine, port, devAddr, io_buflen );
+ i_args.engine, i_args.port, i_args.devAddr, io_buflen );
do
{
// Do Command/Mode reg setups
+ i_args.read_not_write = false;
+
err = i2cSetup( i_target,
io_buflen,
- false, // i_readNotWrite
- i_withStop,
- false, // i_skipModeSetup,
- i_args );
+ i_args);
if( err )
{
@@ -598,7 +618,8 @@ errlHndl_t i2cWrite ( TARGETING::Target * i_target,
err = deviceWrite( i_target,
&fifo.value,
size,
- DEVICE_SCOM_ADDRESS( masterAddrs[engine].fifo ) );
+ DEVICE_SCOM_ADDRESS(
+ masterAddrs[i_args.engine].fifo ) );
if( err )
{
@@ -608,8 +629,8 @@ errlHndl_t i2cWrite ( TARGETING::Target * i_target,
TRACUCOMP( g_trac_i2cr,
"I2C WRITE DATA : engine %.2X : port %.2X : "
"devAddr %.2X : byte %d : %.2X (0x%lx)",
- engine, port, devAddr, bytesWritten,
- fifo.byte_0, fifo.value );
+ i_args.engine, i_args.port, i_args.devAddr,
+ bytesWritten, fifo.byte_0, fifo.value );
}
if( err )
@@ -632,7 +653,7 @@ errlHndl_t i2cWrite ( TARGETING::Target * i_target,
TRACSCOMP( g_trac_i2cr,
"I2C WRITE END : engine %.2X: port %.2X : devAddr %.2X : len %d",
- engine, port, devAddr, io_buflen );
+ i_args.engine, i_args.port, i_args.devAddr, io_buflen );
TRACDCOMP( g_trac_i2c,
EXIT_MRK"i2cWrite()" );
@@ -645,25 +666,19 @@ errlHndl_t i2cWrite ( TARGETING::Target * i_target,
// ------------------------------------------------------------------
errlHndl_t i2cSetup ( TARGETING::Target * i_target,
size_t & i_buflen,
- bool i_readNotWrite,
- bool i_withStop,
- bool i_skipModeSetup,
- input_args_t i_args )
+ misc_args_t & i_args)
{
errlHndl_t err = NULL;
size_t size = sizeof(uint64_t);
- uint64_t port = i_args.port;
- uint64_t engine = i_args.engine;
- uint64_t devAddr = i_args.devAddr;
-
TRACDCOMP( g_trac_i2c,
- ENTER_MRK"i2cSetup(): buf_len=%d, r_nw=%d, w_stop=%d",
- i_buflen, i_readNotWrite, i_withStop );
+ ENTER_MRK"i2cSetup(): buf_len=%d, r_nw=%d, w_stop=%d, sms=%d",
+ i_buflen, i_args.read_not_write, i_args.with_stop,
+ i_args.skip_mode_setup);
// Define the registers that we'll use
- modereg mode;
- cmdreg cmd;
+ mode_reg_t mode;
+ command_reg_t cmd;
do
{
@@ -680,25 +695,24 @@ errlHndl_t i2cSetup ( TARGETING::Target * i_target,
// Skip mode setup on 2nd of 2 cmd strung together - like when sending
// device offset first before read or write
- if ( i_skipModeSetup == false)
+ if ( i_args.skip_mode_setup == false)
{
// Write Mode Register:
- // - bit rate divisor
+ // - bit rate divisor (set in i2cSetClockVariables() )
// - port number
+
mode.value = 0x0ull;
+ mode.bit_rate_div = i_args.bit_rate_divisor;
+ mode.port_num = i_args.port;
- // @todo RTC:72715 - Add multiple bus speed support
- // Hard code to 400KHz until we get attributes in place to get
- // this from the target.
- mode.bit_rate_div = I2C_CLOCK_DIVISOR_400KHZ;
- mode.port_num = port;
TRACUCOMP( g_trac_i2c,"i2cSetup(): set mode = 0x%lx", mode.value);
err = deviceWrite( i_target,
&mode.value,
size,
- DEVICE_SCOM_ADDRESS( masterAddrs[engine].mode));
+ DEVICE_SCOM_ADDRESS(
+ masterAddrs[i_args.engine].mode));
if( err )
{
@@ -714,7 +728,7 @@ errlHndl_t i2cSetup ( TARGETING::Target * i_target,
// - length
cmd.value = 0x0ull;
cmd.with_start = 1;
- cmd.with_stop = (i_withStop ? 1 : 0);
+ cmd.with_stop = (i_args.with_stop ? 1 : 0);
cmd.with_addr = 1;
// cmd.device_addr is 7 bits
@@ -722,9 +736,9 @@ errlHndl_t i2cSetup ( TARGETING::Target * i_target,
// -- value stored in LSB byte of uint64_t
// -- LS-bit is unused, creating the 7 bit cmd.device_addr
// So will be masking for LSB, and then shifting to push off LS-bit
- cmd.device_addr = (0x000000FF & devAddr) >> 1;
+ cmd.device_addr = (0x000000FF & i_args.devAddr) >> 1;
- cmd.read_not_write = (i_readNotWrite ? 1 : 0);
+ cmd.read_not_write = (i_args.read_not_write ? 1 : 0);
cmd.length_b = i_buflen;
TRACUCOMP( g_trac_i2c,"i2cSetup(): set cmd = 0x%lx", cmd.value);
@@ -732,7 +746,8 @@ errlHndl_t i2cSetup ( TARGETING::Target * i_target,
err = deviceWrite( i_target,
&cmd.value,
size,
- DEVICE_SCOM_ADDRESS( masterAddrs[engine].command ) );
+ DEVICE_SCOM_ADDRESS(
+ masterAddrs[i_args.engine].command ) );
if( err )
{
@@ -750,7 +765,7 @@ errlHndl_t i2cSetup ( TARGETING::Target * i_target,
// i2cWaitForCmdComp
// ------------------------------------------------------------------
errlHndl_t i2cWaitForCmdComp ( TARGETING::Target * i_target,
- input_args_t i_args )
+ misc_args_t & i_args)
{
errlHndl_t err = NULL;
uint64_t engine = i_args.engine;
@@ -759,11 +774,11 @@ errlHndl_t i2cWaitForCmdComp ( TARGETING::Target * i_target,
ENTER_MRK"i2cWaitForCmdComp()" );
// Define the registers that we'll use
- statusreg status;
+ status_reg_t status;
- // @todo RTC:72715 - Add multiple bus speed support (set to 400KHz for now)
- uint64_t interval = I2C_TIMEOUT_INTERVAL( I2C_CLOCK_DIVISOR_400KHZ );
- uint64_t timeoutCount = I2C_TIMEOUT_COUNT( interval );
+ // Use Local Variables (timeoutCount gets derecmented)
+ uint64_t interval = i_args.timeout_interval;
+ uint64_t timeoutCount = i_args.timeout_count;
TRACUCOMP(g_trac_i2c, "i2cWaitForCmdComp(): timeoutCount=%d, interval=%d",
timeoutCount, interval);
@@ -824,12 +839,11 @@ errlHndl_t i2cWaitForCmdComp ( TARGETING::Target * i_target,
// i2cReadStatusReg
// ------------------------------------------------------------------
errlHndl_t i2cReadStatusReg ( TARGETING::Target * i_target,
- input_args_t i_args,
- statusreg & o_statusReg )
+ misc_args_t & i_args,
+ status_reg_t & o_statusReg )
{
errlHndl_t err = NULL;
size_t size = sizeof(uint64_t);
- uint64_t engine = i_args.engine;
TRACDCOMP( g_trac_i2c,
ENTER_MRK"i2cReadStatusReg()" );
@@ -840,7 +854,8 @@ errlHndl_t i2cReadStatusReg ( TARGETING::Target * i_target,
err = deviceRead( i_target,
&o_statusReg.value,
size,
- DEVICE_SCOM_ADDRESS( masterAddrs[engine].status ) );
+ DEVICE_SCOM_ADDRESS(
+ masterAddrs[i_args.engine].status ) );
if( err )
{
@@ -849,7 +864,7 @@ errlHndl_t i2cReadStatusReg ( TARGETING::Target * i_target,
TRACUCOMP(g_trac_i2c,"i2cReadStatusReg(): "
INFO_MRK"status[0x%lx]: 0x%016llx",
- masterAddrs[engine].status, o_statusReg.value );
+ masterAddrs[i_args.engine].status, o_statusReg.value );
// Check for Errors
@@ -875,8 +890,8 @@ errlHndl_t i2cReadStatusReg ( TARGETING::Target * i_target,
// i2cCheckForErrors
// ------------------------------------------------------------------
errlHndl_t i2cCheckForErrors ( TARGETING::Target * i_target,
- input_args_t i_args,
- statusreg i_statusVal )
+ misc_args_t & i_args,
+ status_reg_t i_statusVal )
{
errlHndl_t err = NULL;
bool errorFound = false;
@@ -1003,16 +1018,16 @@ errlHndl_t i2cCheckForErrors ( TARGETING::Target * i_target,
// i2cWaitForFifoSpace
// ------------------------------------------------------------------
errlHndl_t i2cWaitForFifoSpace ( TARGETING::Target * i_target,
- input_args_t i_args )
+ misc_args_t & i_args )
{
errlHndl_t err = NULL;
- // @todo RTC:72715 - support multiple bus speeds (set to 400KHz for now)
- uint64_t interval = I2C_TIMEOUT_INTERVAL( I2C_CLOCK_DIVISOR_400KHZ );
- uint64_t timeoutCount = I2C_TIMEOUT_COUNT( interval );
+ // Use Local Variables (timeoutCount gets derecmented)
+ uint64_t interval = i_args.timeout_interval;
+ uint64_t timeoutCount = i_args.timeout_count;
// Define regs we'll be using
- statusreg status;
+ status_reg_t status;
TRACDCOMP( g_trac_i2c,
ENTER_MRK"i2cWaitForFifoSpace()" );
@@ -1096,19 +1111,18 @@ errlHndl_t i2cWaitForFifoSpace ( TARGETING::Target * i_target,
// i2cReset
// ------------------------------------------------------------------
errlHndl_t i2cReset ( TARGETING::Target * i_target,
- input_args_t i_args )
+ misc_args_t & i_args)
{
errlHndl_t err = NULL;
size_t size = sizeof(uint64_t);
// Get Args
- uint64_t engine = i_args.engine;
TRACDCOMP( g_trac_i2c,
ENTER_MRK"i2cReset()" );
// Writing to the Status Register does a full I2C reset.
- statusreg reset;
+ status_reg_t reset;
do
{
@@ -1116,12 +1130,13 @@ errlHndl_t i2cReset ( TARGETING::Target * i_target,
TRACUCOMP(g_trac_i2c,"i2cReset() "
"reset[0x%lx]: 0x%016llx",
- masterAddrs[engine].reset, reset.value );
+ masterAddrs[i_args.engine].reset, reset.value );
err = deviceWrite( i_target,
&reset.value,
size,
- DEVICE_SCOM_ADDRESS( masterAddrs[engine].reset ) );
+ DEVICE_SCOM_ADDRESS(
+ masterAddrs[i_args.engine].reset ) );
if( err )
{
@@ -1152,16 +1167,14 @@ errlHndl_t i2cReset ( TARGETING::Target * i_target,
// i2cSendSlaveStop
// ------------------------------------------------------------------
errlHndl_t i2cSendSlaveStop ( TARGETING::Target * i_target,
- input_args_t i_args )
+ misc_args_t & i_args)
{
errlHndl_t err = NULL;
size_t size = sizeof(uint64_t);
- uint64_t engine = i_args.engine;
- uint64_t port = i_args.port;
// Master Registers
- modereg mode;
- cmdreg cmd;
+ mode_reg_t mode;
+ command_reg_t cmd;
TRACDCOMP( g_trac_i2c,
ENTER_MRK"i2cSendSlaveStop()" );
@@ -1170,11 +1183,8 @@ errlHndl_t i2cSendSlaveStop ( TARGETING::Target * i_target,
{
mode.value = 0x0ull;
- // @todo RTC:72715 - support multiple bus speeds
- // Hard code to 400KHz until we get attributes in place to get
- // this from the target.
- mode.bit_rate_div = I2C_CLOCK_DIVISOR_400KHZ;
- mode.port_num = port;
+ mode.bit_rate_div = i_args.bit_rate_divisor;
+ mode.port_num = i_args.port;
mode.enhanced_mode = 1;
TRACUCOMP(g_trac_i2c,"i2cSendSlaveStop(): "
@@ -1184,7 +1194,8 @@ errlHndl_t i2cSendSlaveStop ( TARGETING::Target * i_target,
err = deviceWrite( i_target,
&mode.value,
size,
- DEVICE_SCOM_ADDRESS( masterAddrs[engine].mode ) );
+ DEVICE_SCOM_ADDRESS(
+ masterAddrs[i_args.engine].mode ) );
if( err )
{
@@ -1201,7 +1212,8 @@ errlHndl_t i2cSendSlaveStop ( TARGETING::Target * i_target,
err = deviceWrite( i_target,
&cmd.value,
size,
- DEVICE_SCOM_ADDRESS( masterAddrs[engine].command ) );
+ DEVICE_SCOM_ADDRESS(
+ masterAddrs[i_args.engine].command ) );
if( err )
{
@@ -1229,15 +1241,14 @@ errlHndl_t i2cSendSlaveStop ( TARGETING::Target * i_target,
// i2cGetInterrupts
// ------------------------------------------------------------------
errlHndl_t i2cGetInterrupts ( TARGETING::Target * i_target,
- input_args_t i_args,
+ misc_args_t & i_args,
uint64_t & o_intRegValue )
{
errlHndl_t err = NULL;
size_t size = sizeof(uint64_t);
- uint64_t engine = i_args.engine;
// Master Regs
- interruptreg intreg;
+ interrupt_reg_t intreg;
TRACDCOMP( g_trac_i2c,
ENTER_MRK"i2cGetInterrupts()" );
@@ -1248,7 +1259,8 @@ errlHndl_t i2cGetInterrupts ( TARGETING::Target * i_target,
err = deviceRead( i_target,
&intreg.value,
size,
- DEVICE_SCOM_ADDRESS( masterAddrs[engine].interrupt ) );
+ DEVICE_SCOM_ADDRESS(
+ masterAddrs[i_args.engine].interrupt ) );
if( err )
{
@@ -1277,10 +1289,12 @@ errlHndl_t i2cGetInterrupts ( TARGETING::Target * i_target,
errlHndl_t i2cSetupMasters ( void )
{
errlHndl_t err = NULL;
-
- modereg mode;
size_t size = sizeof(uint64_t);
+ misc_args_t io_args;
+
+ mode_reg_t mode;
+
TRACDCOMP( g_trac_i2c,
ENTER_MRK"i2cSetupMasters()" );
@@ -1346,14 +1360,32 @@ errlHndl_t i2cSetupMasters ( void )
// Write Mode Register:
mode.value = 0x0ull;
- // @todo RTC:72715 - support multiple bus speeds
- // Hard code to 400KHz until we get attributes in place
- // to get this from the target.
- mode.bit_rate_div = I2C_CLOCK_DIVISOR_400KHZ;
+ // Hardcode to 400KHz for PHYP
+ err = i2cSetBusVariables ( centList[centaur],
+ SET_I2C_BUS_400KHZ,
+ io_args );
+
+ if( err )
+ {
+ TRACFCOMP( g_trac_i2c,
+ ERR_MRK"i2cSetupMasters: Error Setting Bus "
+ "Speed Variables-Centaur, engine: %d",
+ engine );
+
+ // If we get error skip setting this target, but still need
+ // to continue to program the I2C Bus Divisor for the rest
+ errlCommit( err,
+ I2C_COMP_ID );
+ continue;
+ }
+
+ mode.bit_rate_div = io_args.bit_rate_divisor;
+
err = deviceWrite( centList[centaur],
&mode.value,
size,
- DEVICE_SCOM_ADDRESS( masterAddrs[engine].mode ) );
+ DEVICE_SCOM_ADDRESS(
+ masterAddrs[engine].mode));
if( err )
{
@@ -1434,14 +1466,33 @@ errlHndl_t i2cSetupMasters ( void )
// Write Mode Register:
mode.value = 0x0ull;
- // @todo RTC:72715 - support multiple bus speeds
- // Hard code to 400KHz until we get attributes in place
- // to get this from the target.
- mode.bit_rate_div = I2C_CLOCK_DIVISOR_400KHZ;
+ // Hardcode to 400KHz for PHYP
+ err = i2cSetBusVariables ( procList[proc],
+ SET_I2C_BUS_400KHZ,
+ io_args );
+
+ if( err )
+ {
+ TRACFCOMP( g_trac_i2c,
+ ERR_MRK"i2cSetupMasters: Error Setting Bus "
+ "Speed Variables-Processor, engine: %d",
+ engine );
+
+ // If we get error skip setting this target, but still need
+ // to continue to program the I2C Bus Divisor for the rest
+ errlCommit( err,
+ I2C_COMP_ID );
+
+ continue;
+ }
+
+ mode.bit_rate_div = io_args.bit_rate_divisor;
+
err = deviceWrite( procList[proc],
&mode.value,
size,
- DEVICE_SCOM_ADDRESS( masterAddrs[engine].mode ) );
+ DEVICE_SCOM_ADDRESS(
+ masterAddrs[engine].mode));
if( err )
{
@@ -1476,4 +1527,85 @@ errlHndl_t i2cSetupMasters ( void )
}
+
+// ------------------------------------------------------------------
+// i2cSetClockVariables
+// ------------------------------------------------------------------
+errlHndl_t i2cSetBusVariables ( TARGETING::Target * i_target,
+ i2c_bus_setting_mode_t i_mode,
+ misc_args_t & io_args)
+{
+ errlHndl_t err = NULL;
+
+ TRACDCOMP( g_trac_i2c,
+ ENTER_MRK"i2cSetBusVariables()" );
+
+ do
+ {
+
+ // @todo RTC:80614 - Read I2C bus speed attributes from I2C Master
+ // For now, hardcode to 400KHz
+ i_mode = SET_I2C_BUS_400KHZ;
+
+ if (i_mode == SET_I2C_BUS_400KHZ)
+ {
+
+ io_args.bus_speed = 400;
+ io_args.bit_rate_divisor = I2C_CLOCK_DIVISOR_400KHZ;
+ io_args.timeout_interval = I2C_TIMEOUT_INTERVAL(
+ I2C_CLOCK_DIVISOR_400KHZ);
+ io_args.timeout_count = I2C_TIMEOUT_COUNT(
+ io_args.timeout_interval);
+
+
+ }
+
+ /* @todo RTC:80614 - sync up reading attributes with MRW
+ else if (i_mode == READ_I2C_BUS_ATTRIBUTES)
+ {
+
+ }
+ */
+
+ else
+ {
+ TRACFCOMP( g_trac_i2c, ERR_MRK"i2cSetBusVariables: "
+ "Invalid Bus Speed Mode Input!" );
+
+ /*@
+ * @errortype
+ * @reasoncode I2C_INVALID_BUS_SPEED_MODE
+ * @severity ERRORLOG::ERRL_SEV_UNRECOVERABLE
+ * @moduleid I2C_SET_BUS_VARIABLES
+ * @userdata1 I2C Bus Setting Mode Enum
+ * @userdata2 <UNUSED>
+ * @frucallout <NONE>
+ * @devdesc Invalid I2C bus speed mode input
+ */
+ err = new ERRORLOG::ErrlEntry( ERRORLOG::ERRL_SEV_UNRECOVERABLE,
+ I2C_SET_BUS_VARIABLES,
+ I2C_INVALID_BUS_SPEED_MODE,
+ i_mode,
+ 0x0 );
+ break;
+
+ }
+
+
+ } while( 0 );
+
+
+ TRACUCOMP(g_trac_i2c,"i2cSetBusVariables(): e/p/dA=%d/%d/0x%x: "
+ "mode=%d: b_sp=%d, b_r_d=0x%x, to_i=%d, to_c = %d",
+ io_args.engine, io_args.port, io_args.devAddr,
+ i_mode, io_args.bus_speed, io_args.bit_rate_divisor,
+ io_args.timeout_interval, io_args.timeout_count);
+
+ TRACDCOMP( g_trac_i2c,
+ EXIT_MRK"i2cSetBusVariables()" );
+
+ return err;
+}
+
+
} // end namespace I2C
diff --git a/src/usr/i2c/i2c.H b/src/usr/i2c/i2c.H
index d1b3b2afd..e864df093 100755
--- a/src/usr/i2c/i2c.H
+++ b/src/usr/i2c/i2c.H
@@ -105,7 +105,7 @@ namespace I2C
/**
* @brief I2C Master register structure and address definition
*/
-typedef struct
+struct i2c_addrs_t
{
uint64_t fifo;
uint64_t command;
@@ -114,9 +114,11 @@ typedef struct
uint64_t interrupt;
uint64_t status;
uint64_t reset;
-} i2c_addrs_t;
+};
-// Addresses for each of the registers in each engine.
+/**
+ * @brief Addresses for each of the registers in each engine.
+ */
static i2c_addrs_t masterAddrs[] =
{
{ /* Master 0 */
@@ -148,6 +150,34 @@ static i2c_addrs_t masterAddrs[] =
}
};
+/**
+ * @brief Structure used to pass important variables between functions
+ */
+struct misc_args_t
+{
+ uint8_t port;
+ uint8_t engine;
+ uint64_t devAddr;
+ bool skip_mode_setup;
+ bool with_stop;
+ bool read_not_write;
+ uint64_t bus_speed; // in kbits/sec (ie 400KHz)
+ uint16_t bit_rate_divisor; // uint16_t to match size in mode register
+ uint64_t timeout_interval;
+ uint64_t timeout_count;
+};
+
+/**
+ * @brief Different ways of setting the I2C Bus Speed
+ */
+enum i2c_bus_setting_mode_t
+{
+ READ_I2C_BUS_ATTRIBUTES,
+ SET_I2C_BUS_400KHZ,
+ LAST_BUS_SETTING_MODE_TYPE
+};
+
+
// -----------------------------------------------------------------------
// NOTE: Addressing listed below is from the PIB I2C Master Addressing
@@ -159,7 +189,7 @@ static i2c_addrs_t masterAddrs[] =
* @brief I2C FIFO register definition
* Address 0x04
*/
-union fiforeg
+union fifo_reg_t
{
uint64_t value;
struct
@@ -167,13 +197,13 @@ union fiforeg
uint64_t byte_0 : 8;
uint64_t padding : 56;
} PACKED;
-} fifo_reg_t;
+};
/**
* @brief I2C Command register definition
* Address 0x05
*/
-union cmdreg
+union command_reg_t
{
uint64_t value;
struct
@@ -188,13 +218,13 @@ union cmdreg
uint64_t length_b : 16;
uint64_t padding : 32;
} PACKED;
-} command_reg_t;
+};
/**
* @brief I2C Mode register definition
* Address 0x06
*/
-union modereg
+union mode_reg_t
{
uint64_t value;
struct
@@ -208,13 +238,13 @@ union modereg
uint64_t wrap_mode : 1;
uint64_t padding : 32;
} PACKED;
-} mode_reg_t;
+};
/**
* @brief Watermark register definition
* Address 0x07
*/
-union watermarkreg
+union watermark_reg_t
{
uint64_t value;
struct
@@ -226,13 +256,13 @@ union watermarkreg
uint64_t reserved2 : 4;
uint64_t padding : 32;
} PACKED;
-} watermark_reg_t;
+};
/**
* @brief Interrupt Mask register definition
* Address 0x08
*/
-union intmaskreg
+union interrupt_mask_reg_t
{
uint64_t value;
struct
@@ -256,13 +286,13 @@ union intmaskreg
uint64_t sda_eq_0 : 1;
uint64_t padding : 32;
} PACKED;
-} interrupt_mask_reg_t;
+};
/**
* @brief Interrupt Condition register definition
* Address 0x09
*/
-union intcondreg
+union interrupt_cond_reg_t
{
uint64_t value;
struct
@@ -286,13 +316,13 @@ union intcondreg
uint64_t sda_eq_0 : 1;
uint64_t padding : 32;
} PACKED;
-} interrupt_cond_reg_t;
+};
/**
* @brief Interrupt register definition
* Address 0x0A
*/
-union interruptreg
+union interrupt_reg_t
{
uint64_t value;
struct
@@ -316,13 +346,13 @@ union interruptreg
uint64_t sda_eq_0 : 1;
uint64_t padding: 32;
} PACKED;
-} interrupt_reg_t;
+};
/**
* @brief Status register definition
* Address 0x0B
*/
-union statusreg
+union status_reg_t
{
uint64_t value;
struct
@@ -347,13 +377,13 @@ union statusreg
uint64_t fifo_entry_count : 8;
uint64_t padding : 32;
} PACKED;
-} status_reg_t;
+};
/**
* @brief Extended Status register definition
* Address 0x0C
*/
-union extstatusreg
+union extended_status_reg_t
{
uint64_t value;
struct
@@ -375,13 +405,13 @@ union extstatusreg
uint64_t i2c_version : 5;
uint64_t padding : 32;
} PACKED;
-} extended_status_reg_t;
+};
/**
* @brief Residual Front/Back end length register definition
* Address 0x0D
*/
-union residuallengthreg
+union residual_length_reg_t
{
uint64_t value;
struct
@@ -390,14 +420,8 @@ union residuallengthreg
uint64_t back_end_length : 16;
uint64_t padding : 32;
} PACKED;
-} residual_length_reg_t;
+};
-typedef struct
-{
- uint64_t port;
- uint64_t engine;
- uint64_t devAddr;
-} input_args_t;
/**
@@ -451,9 +475,6 @@ errlHndl_t i2cPerformOp( DeviceFW::OperationType i_opType,
* @param[in] i_buflen - The size of the data to read and place in the
* buffer.
*
- * @param[in] i_skipModeSetup - true if mode register setup needs to be
- * skipped
- *
* @param[in] i_args - Structure containing arguments needed for a command
* transaction.
*
@@ -463,8 +484,7 @@ errlHndl_t i2cPerformOp( DeviceFW::OperationType i_opType,
errlHndl_t i2cRead ( TARGETING::Target * i_target,
void * o_buffer,
size_t & i_buflen,
- bool & i_skipModeSetup,
- input_args_t i_args );
+ misc_args_t & i_args);
/**
* @brief This function will do the real work of writinging to the I2C
@@ -478,9 +498,6 @@ errlHndl_t i2cRead ( TARGETING::Target * i_target,
* @param[in/out] io_buflen - INPUT: The size of the data to write to the
* target device. OUTPUT: The size of the data buffer written.
*
- * @param[in] i_withStop - true if with_stop bit is to be set on operation;
- * otherwise, with_stop bit will be set to zero.
- *
* @param[in] i_args - Structure containing arguments needed for a command
* transaction.
*
@@ -491,8 +508,7 @@ errlHndl_t i2cRead ( TARGETING::Target * i_target,
errlHndl_t i2cWrite ( TARGETING::Target * i_target,
void * i_buffer,
size_t & io_buflen,
- bool & i_withStop,
- input_args_t i_args );
+ misc_args_t & i_args);
/**
* @brief This function will do the I2C setup of the Address/Command registers
@@ -502,15 +518,6 @@ errlHndl_t i2cWrite ( TARGETING::Target * i_target,
*
* @param[in] i_buflen - The size of the data that will be read/written.
*
- * @param[in] i_readNotWrite - true if doing a read operation, false if
- * doing a write operation.
- *
- * @param[in] i_withStop - true if with_stop bit is to be set, otherwise
- * with_stop will be set to zero.
- *
- * @param[in] i_skipModeSetup - true if mode register setup needs to be
- * skipped
- *
* @param[in] i_args - Structure containing arguments needed for a command
* transaction.
*
@@ -519,10 +526,7 @@ errlHndl_t i2cWrite ( TARGETING::Target * i_target,
*/
errlHndl_t i2cSetup ( TARGETING::Target * i_target,
size_t & i_buflen,
- bool i_readNotWrite,
- bool i_withStop,
- bool i_skipModeSetup,
- input_args_t i_args );
+ misc_args_t & i_args);
/**
* @brief This function will wait for the command to be complete or
@@ -537,7 +541,7 @@ errlHndl_t i2cSetup ( TARGETING::Target * i_target,
* the error log.
*/
errlHndl_t i2cWaitForCmdComp ( TARGETING::Target * i_target,
- input_args_t i_args );
+ misc_args_t & i_args);
/**
* @brief This function will read the I2C Master engine status register
@@ -554,8 +558,8 @@ errlHndl_t i2cWaitForCmdComp ( TARGETING::Target * i_target,
* the error log.
*/
errlHndl_t i2cReadStatusReg ( TARGETING::Target * i_target,
- input_args_t i_args,
- statusreg & o_statusReg );
+ misc_args_t & i_args,
+ status_reg_t & o_statusReg );
/**
* @brief This function will check for errors in the status register
@@ -572,8 +576,8 @@ errlHndl_t i2cReadStatusReg ( TARGETING::Target * i_target,
* the error log.
*/
errlHndl_t i2cCheckForErrors ( TARGETING::Target * i_target,
- input_args_t i_args,
- statusreg i_statusVal );
+ misc_args_t & i_args,
+ status_reg_t i_statusVal );
/**
* @brief This function will read the status register and not return
@@ -590,7 +594,7 @@ errlHndl_t i2cCheckForErrors ( TARGETING::Target * i_target,
* the error log.
*/
errlHndl_t i2cWaitForFifoSpace ( TARGETING::Target * i_target,
- input_args_t i_args );
+ misc_args_t & i_args);
/**
* @brief This function will reset the I2C Master engine specified
@@ -606,7 +610,7 @@ errlHndl_t i2cWaitForFifoSpace ( TARGETING::Target * i_target,
* the error log.
*/
errlHndl_t i2cReset ( TARGETING::Target * i_target,
- input_args_t i_args );
+ misc_args_t & i_args );
/**
* @brief This function will send the Stop command to the slave device
@@ -621,7 +625,7 @@ errlHndl_t i2cReset ( TARGETING::Target * i_target,
* the error log.
*/
errlHndl_t i2cSendSlaveStop ( TARGETING::Target * i_target,
- input_args_t i_args );
+ misc_args_t & i_args );
/**
* @brief This function will read the interrupt register and return the
@@ -639,9 +643,27 @@ errlHndl_t i2cSendSlaveStop ( TARGETING::Target * i_target,
* the error log.
*/
errlHndl_t i2cGetInterrupts ( TARGETING::Target * i_target,
- input_args_t i_args,
+ misc_args_t & i_args,
uint64_t & o_intRegValue );
+/**
+ * @brief This function calculates the different variables related to the
+ * I2C Bus Speed that are used in the other functions
+ *
+ * @param[in] i_target - The I2C master target.
+ *
+ * @param[in] i_mode - States how bus setting will be determined
+ *
+ * @param[in/out] io_args - Structure containing arguments needed for a command
+ * transaction. Clock arguments set in this function.
+ *
+ * @return errHndl_t - NULL if successful, otherwise a pointer to
+ * the error log.
+ */
+errlHndl_t i2cSetBusVariables ( TARGETING::Target * i_target,
+ i2c_bus_setting_mode_t i_mode,
+ misc_args_t & io_args );
+
}; // end I2C namespace
diff --git a/src/usr/i2c/test/eepromddtest.H b/src/usr/i2c/test/eepromddtest.H
index 48b6329cc..d8e0fef9f 100755
--- a/src/usr/i2c/test/eepromddtest.H
+++ b/src/usr/i2c/test/eepromddtest.H
@@ -28,14 +28,15 @@
*
* @brief Test cases for the eeprom dd code
*/
-#include <sys/time.h>
+#include <sys/time.h>
#include <cxxtest/TestSuite.H>
#include <errl/errlmanager.H>
#include <errl/errlentry.H>
#include <devicefw/driverif.H>
#include <i2c/eepromddreasoncodes.H>
#include <targeting/common/commontargeting.H>
+#include <pnor/pnorif.H>
#include "i2ctest.H"
#include "../eepromdd.H"
@@ -47,7 +48,6 @@ using namespace TARGETING;
using namespace EEPROM;
-
class EEPROMTest: public CxxTest::TestSuite
{
public:
@@ -63,10 +63,6 @@ class EEPROMTest: public CxxTest::TestSuite
int fails = 0;
int num_ops = 0;
- uint8_t* testBuffer = NULL;
- uint8_t* testBuffer_read = NULL;
-
-
TRACFCOMP( g_trac_eeprom,
"testEEPROMReadWrite - Start" );
@@ -151,8 +147,8 @@ class EEPROMTest: public CxxTest::TestSuite
for( uint32_t j = 0; j < fullList.size(); j++ )
{
// Skip this target if EEPROM isn't available. or if non functional
- if( !isI2CAvailable( fullList[j] ) ||
- !fullList[j]->getAttr<TARGETING::ATTR_HWAS_STATE>().functional)
+ if( !fullList[j]->getAttr<TARGETING::ATTR_HWAS_STATE>()\
+ .functional)
{
continue;
}
@@ -208,93 +204,256 @@ class EEPROMTest: public CxxTest::TestSuite
}
}
- // Test EEPROM Write of large size
- // @todo RTC:69113 - will clean this up:
- // 1) Make its own testcase function
- // 2) Will use a larger data set: Plan on using 4K header of
- // test_signed_container and putting it into un-used area of
- // SBE_BACKUP
- // 3) Will restore original data just in case
- uint64_t testBufLen = 0xF1;
- testBuffer = static_cast<uint8_t*>(malloc(testBufLen));
- memset(testBuffer, 0xFE, testBufLen);
-
- // Randomize the Data a bit
- for (uint64_t i = 0;
- i < ((testBufLen / 8) + 1);
- i++)
- testBuffer[i*8] = i;
-
- for (uint64_t k = 0; k < 8; k++)
- testBuffer[k] = k;
-
- // do the Write operation
- err = deviceOp( DeviceFW::WRITE,
- fullList[0],
- testBuffer,
- testBufLen,
- DEVICE_EEPROM_ADDRESS(SBE_BACKUP,0x0));
- if( err )
- {
- TS_FAIL( "testEEPROMReadWrite - FAIL on large Data Write");
- errlCommit( err,
- EEPROM_COMP_ID );
- delete err;
- break;
- }
+ } while( 0 );
- // Read Back and Compare
- testBuffer_read = static_cast<uint8_t*>(malloc( testBufLen ));
+ TRACFCOMP( g_trac_eeprom,
+ "testEEPROMReadWrite - End: %d/%d fails",
+ fails, num_ops );
+ }
- // clear read buffer
- memset (testBuffer_read, 0, testBufLen);
- // do the Read operation
- err = deviceOp( DeviceFW::READ,
- fullList[0],
- testBuffer_read,
- testBufLen,
- DEVICE_EEPROM_ADDRESS(SBE_BACKUP,0x0));
+ /**
+ * @brief EEPROM Read/Write Large Test
+ * This test will read and write 1KB of data to SBE Backup
+ * VPD. It will attempt to restore the original data at
+ * the end of the test.
+ *
+ * Note: 1st 1K of SBE EEPROM data is currently blank, so this
+ * test will read and write to that address space
+ */
+ void testEEPROMReadWriteLarge ( void )
+ {
+ errlHndl_t err = NULL;
+ int fails = 0;
+ int num_ops = 0;
+ int cmds = 0;
+
+ // Create 1KB buffers
+ size_t testBufLen = 1024;
+ uint8_t testBuffer[testBufLen];
+ uint8_t new_data[testBufLen];
+ uint8_t original_data[testBufLen];
+
+
+ TRACFCOMP( g_trac_eeprom,
+ "testEEPROMReadWriteLarge - Start" );
+
+ // Skipping EEPROM test altogether in VBU/VPO environment
+ if( TARGETING::is_vpo() )
+ {
+ return;
+ }
+
+ do
+ {
+ // Get a processor Target
+ TARGETING::TargetService& l_targetService =
+ TARGETING::targetService();
+ TARGETING::Target* testTarget = NULL;
+ l_targetService.masterProcChipTargetHandle( testTarget );
+ assert(testTarget != NULL);
+ TargetHandleList fullList;
+ fullList.push_back( testTarget );
+
+ // 5 operations of 1K data per target (details below)
+ const uint32_t NUM_CMDS = 5;
+
+ // Number of total operations
+ num_ops = fullList.size() * NUM_CMDS;
+
+ /************************************************************/
+ /* Using PNOR to return the extended image to use as new_data */
+ /**************************************************************/
+ // Jumping 32K into extended image for more dense data
+ static const uint64_t HEADER_OFFSET = 0x8000;
+ PNOR::SectionInfo_t pnorSectionInfo;
- if( err )
+ err = PNOR::getSectionInfo(PNOR::HB_EXT_CODE,
+ PNOR::CURRENT_SIDE,
+ pnorSectionInfo);
+
+ if ( err ||
+ (pnorSectionInfo.size < HEADER_OFFSET + testBufLen)
+ )
{
- TS_FAIL( "testEEPROMReadWrite - FAIL on large Data Read");
- errlCommit( err,
- EEPROM_COMP_ID );
+ TS_FAIL("testEEPROMReadWriteLarge: PNOR::getSectionInfo failed or size too small: pnorSize=0x%X, HEADER_OFFSET=0x%X, testBufLen = 0x%X", pnorSectionInfo.size, HEADER_OFFSET, testBufLen);
+ errlCommit(err, EEPROM_COMP_ID);
delete err;
+ fails++;
break;
}
- // Compare the data
- if ( memcmp( testBuffer, testBuffer_read, testBufLen) )
+ void* tmp_ptr = reinterpret_cast<void*>(pnorSectionInfo.vaddr +
+ HEADER_OFFSET);
+
+ if (tmp_ptr == NULL)
{
- TS_FAIL( "testEEPROMReadWrite - MISCOMPARE on large Data");
+ TS_FAIL("testEEPROMReadWriteLarge: Couldn't get tmp_ptr for new data");
+ errlCommit(err, EEPROM_COMP_ID);
+ delete err;
+ fails++;
break;
+
}
- else
+
+ // Valid Buffer, so memcpy the first 1KB
+ memcpy( new_data, tmp_ptr, testBufLen );
+
+
+ /************************************************************/
+ /* Loop through targets and perform operations */
+ /************************************************************/
+
+ for( uint32_t i = 0; i < fullList.size(); i++ )
{
- TRACUCOMP( g_trac_eeprom, "testEEPROMReadWrite - large "
- "Data R/W Successful");
- }
+ // Skip this target if EEPROM isn't available
+ // or if non functional
+ if( !fullList[i]->getAttr<TARGETING::ATTR_HWAS_STATE>()\
+ .functional)
+ {
+ continue;
+ }
- } while( 0 );
- // Clean up malloc'ed buffers
- if ( testBuffer != NULL)
- {
- free(testBuffer);
- }
+ // Before starting, clear original data buffer
+ memset(original_data, 0x0, testBufLen);
- if ( testBuffer_read != NULL)
- {
- free(testBuffer_read);
- }
+ for (uint8_t j = 1; j <= NUM_CMDS; j++)
+ {
+
+ // Details: 5 operations of 1K data per target
+ // 1) Read Original Data and Save It
+ // 2) Write New Data
+ // 3) Read New Data and Compare
+ // 4) Write Back Original Data
+ // 5) Read Back Original Data and Compare
+
+ // Clear data buffer before reads
+ if ( (j == 1) || (j == 3) || (j == 5) )
+ {
+ memset(testBuffer, 0x0, testBufLen);
+ }
+
+ // For Loop 2: set data to new data
+ if ( j == 2 )
+ {
+ memcpy(testBuffer, new_data, testBufLen);
+ }
+ // For Loop 4: set data to original_data
+ if ( j == 4 )
+ {
+ memcpy(testBuffer, original_data, testBufLen);
+ }
+
+ // increment cmd op counter
+ cmds++;
+
+ // do the Operation
+ err = deviceOp(
+ (j%2) ? DeviceFW::READ : DeviceFW::WRITE,
+ fullList[0],
+ testBuffer,
+ testBufLen,
+ DEVICE_EEPROM_ADDRESS(SBE_BACKUP,0x0));
+
+ if( err )
+ {
+ TS_FAIL( "testEEPROMReadWriteLarge = OP %d FAILED "
+ "- cmd %d out of %d",
+ j, i, NUM_CMDS );
+ errlCommit( err,
+ EEPROM_COMP_ID );
+ delete err;
+ fails++;
+ continue;
+ }
+
+
+ // Handle loop-specific results
+
+ // For Loop 1: save original data
+ if ( j == 1 )
+ {
+ memcpy(original_data, testBuffer, testBufLen);
+
+ TRACUCOMP(g_trac_eeprom,"testEEPROMReadWriteLarge:"
+ " saving original data. i=%d, j=%d",
+ i, j);
+ }
+
+ // For Loop 3: compare new data
+ if ( j == 3 )
+ {
+ // Compare the data
+ if ( memcmp(testBuffer, new_data, testBufLen) )
+ {
+ TRACFCOMP(g_trac_eeprom,
+ "testEEPROMReadWriteLarge: MISCOMPARE"
+ " of new data, len=0x%X", testBufLen);
+
+ TRACFBIN( g_trac_eeprom, "testBuffer=",
+ testBuffer, testBufLen);
+ TRACFBIN( g_trac_eeprom, "new_data=",
+ new_data, testBufLen);
+ TS_FAIL( "testEEPROMReadWriteLarge - MISCOMPARE"
+ " on writing new data");
+ fails++;
+
+ // Don't break - try to write back original data
+ continue;
+ }
+ else
+ {
+ TRACUCOMP(g_trac_eeprom,
+ "testEEPROMReadWriteLarge: New "
+ "Data R/W Successful i=%d,j=%d",
+ i, j);
+ }
+ }
+
+
+ // For Loop 5: compare writing-back original data
+ if ( j == 5 )
+ {
+ // Compare the data
+ if ( memcmp(testBuffer, original_data, testBufLen) )
+ {
+ TRACFCOMP(g_trac_eeprom,
+ "testEEPROMReadWriteLarge: MISCOMPARE"
+ " of original data, len=0x%X",
+ testBufLen);
+
+ TRACFBIN( g_trac_eeprom, "testBuffer=",
+ testBuffer, testBufLen);
+ TRACFBIN( g_trac_eeprom, "orig_data=",
+ original_data, testBufLen);
+
+ TS_FAIL( "testEEPROMReadWriteLarge - MISCOMPARE"
+ " on writing back original data");
+ fails++;
+
+ break;
+ }
+ else
+ {
+ TRACUCOMP(g_trac_eeprom,
+ "testEEPROMReadWriteLarge: Original "
+ "Data R/W Successful i=%d,j=%d",
+ i, j);
+ }
+ }
+
+ } // end of 'j' loop: 5 ops per target
+
+ } // end of 'i' loop: target loop
+
+ } while( 0 );
TRACFCOMP( g_trac_eeprom,
- "testEEPROMReadWrite - %d/%d fails",
+ "testEEPROMReadWriteLarge - End: %d/%d fails",
fails, num_ops );
}
@@ -310,6 +469,9 @@ class EEPROMTest: public CxxTest::TestSuite
uint64_t data = 0x0ull;
size_t dataSize = 8;
+ TRACFCOMP( g_trac_eeprom,
+ "testEEPROMInvalidOperation - Start" );
+
do
{
// Get a processor Target
@@ -318,10 +480,9 @@ class EEPROMTest: public CxxTest::TestSuite
tS.masterProcChipTargetHandle( testTarget );
assert(testTarget != NULL);
- // Skip this target if EEPROM isn't available or target is non
- // functional
- if( !isI2CAvailable( testTarget ) ||
- !testTarget->getAttr<TARGETING::ATTR_HWAS_STATE>().functional)
+ // Skip this target if target is non-functional
+ if(!testTarget->getAttr<TARGETING::ATTR_HWAS_STATE>().\
+ functional)
{
continue;
}
@@ -337,23 +498,96 @@ class EEPROMTest: public CxxTest::TestSuite
if( NULL == err )
{
fails++;
- TS_FAIL( "Error should've resulted in Operation type of LAST_OP_TYPE!" );
+ TS_FAIL( "testEEPROMInvalidOperation - Error should've "
+ " resulted in Operation type of LAST_OP_TYPE!" );
}
else
{
+ TRACUCOMP(g_trac_eeprom, "testEEPROMInvalidOperation - "
+ "Error log returned as expected. RC=0x%X",
+ err->reasonCode() );
delete err;
err = NULL;
}
} while( 0 );
TRACFCOMP( g_trac_eeprom,
- "testEEPROMInvalidOperation - %d/%d fails",
+ "testEEPROMInvalidOperation - End: %d/%d fails",
fails, num_ops );
}
+
+ /**
+ * @brief EEPROM Overflow Test
+ * This test will pass in a target which does not have an
+ * EEPROM attribute associated with it. It is expected that i
+ * an error log is to be returned.
+ */
+ void testEEPROMOverflow ( void )
+ {
+ errlHndl_t err = NULL;
+ int64_t fails = 0, num_ops = 0;
+ uint64_t data = 0x0ull;
+ size_t dataSize = 0;
+ uint64_t offset = 0x0ull;
+
+ TRACFCOMP( g_trac_eeprom,
+ "testEEPROMOverflow - Start" );
+
+ do
+ {
+ // Get a processor Target
+ TARGETING::TargetService& tS = TARGETING::targetService();
+ TARGETING::Target* testTarget = NULL;
+ tS.masterProcChipTargetHandle( testTarget );
+ assert(testTarget != NULL);
+
+ // Skip this target if target is non-functional
+ if(!testTarget->getAttr<TARGETING::ATTR_HWAS_STATE>()
+ .functional)
+ {
+ continue;
+ }
+
+ // Set max length and offset
+ dataSize = 0xFFFFFFFFFFFFFFFF;
+ offset = 0xFFFFFFFFFFFFFFFF;
+
+ num_ops++;
+ err = deviceOp( DeviceFW::WRITE,
+ testTarget,
+ &data,
+ dataSize,
+ DEVICE_EEPROM_ADDRESS( 0x0,
+ offset ) );
+
+ if( NULL == err )
+ {
+ fails++;
+ TS_FAIL( "testEEPROMOverflow - Error should've "
+ "resulted from overflow offset and length: "
+ "offset=0x%X, length = 0x%x",
+ offset, dataSize);
+ }
+ else
+ {
+ TRACUCOMP(g_trac_eeprom, "testEEPROMOverflow - "
+ "Error log returned as expectede. RC=0x%X",
+ err->reasonCode() );
+ delete err;
+ err = NULL;
+ }
+ } while( 0 );
+
+ TRACFCOMP( g_trac_eeprom,
+ "testEEPROMInvalidChip - End: %d/%d fails",
+ fails, num_ops );
+ }
+
+
/**
* @brief EEPROM Invalid Chip Test
* This test will pass in an invalid chip identifier which should
- * result in an error being returned back from
+ * result in an error being returned.
*/
void testEEPROMInvalidChip ( void )
{
@@ -362,19 +596,21 @@ class EEPROMTest: public CxxTest::TestSuite
uint64_t data = 0x0ull;
size_t dataSize = 8;
+ TRACFCOMP( g_trac_eeprom,
+ "testEEPROMInvalidChip - Start" );
do
{
+
// Get a processor Target
TARGETING::TargetService& tS = TARGETING::targetService();
TARGETING::Target* testTarget = NULL;
tS.masterProcChipTargetHandle( testTarget );
assert(testTarget != NULL);
- // Skip this target if EEPROM isn't available. or target is non
- // functional
- if( !isI2CAvailable( testTarget ) ||
- !testTarget->getAttr<TARGETING::ATTR_HWAS_STATE>().functional)
+ // Skip this target if target is non-functional
+ if(!testTarget->getAttr<TARGETING::ATTR_HWAS_STATE>()
+ .functional)
{
continue;
}
@@ -390,21 +626,28 @@ class EEPROMTest: public CxxTest::TestSuite
if( NULL == err )
{
fails++;
- TS_FAIL( "Error should've resulted in using EEPROM chip %d!",
+ TS_FAIL( "testEEPROMInvalidChip - Error should've "
+ "resulted in using EEPROM chip %d!",
LAST_CHIP_TYPE );
}
else
{
+ TRACUCOMP(g_trac_eeprom, "testEEPROMInvalidChip - "
+ "Error log returned as expected. RC=0x%x ",
+ err->reasonCode() );
delete err;
err = NULL;
}
+
} while( 0 );
TRACFCOMP( g_trac_eeprom,
- "testEEPROMInvalidChip - %d/%d fails",
+ "testEEPROMInvalidChip - End: %d/%d fails",
fails, num_ops );
}
+
+
};
#endif
diff --git a/src/usr/i2c/test/i2ctest.H b/src/usr/i2c/test/i2ctest.H
index 12b12385f..15fe1f226 100755
--- a/src/usr/i2c/test/i2ctest.H
+++ b/src/usr/i2c/test/i2ctest.H
@@ -35,6 +35,7 @@
#include <errl/errlentry.H>
#include <devicefw/driverif.H>
#include <i2c/i2creasoncodes.H>
+#include <i2c/i2cif.H>
#include <targeting/common/predicates/predicates.H>
#include <targeting/common/attributes.H>
@@ -50,33 +51,6 @@ using namespace TARGETING;
// Used to ignore comparing data on reads
#define I2C_TEST_IGNORE_DATA_COMPARE 0xFFFFFFFFFFFFFFFF
-// @todo RTC:72715: Re-visit the use of this function when we have full
-// Attribute support
-bool isI2CAvailable( TARGETING::Target * i_target )
-{
- bool avail = true;
-
- // Rudimentary Check - Every I2C Master has VPD Primary Attribute
- EepromVpdPrimaryInfo eepromData;
- if( i_target->tryGetAttr<ATTR_EEPROM_VPD_PRIMARY_INFO>( eepromData ) )
- {
-
- if( ( 0x80 == eepromData.port ) &&
- ( 0x80 == eepromData.devAddr ) &&
- ( 0x80 == eepromData.engine ) )
- {
- // Default values, thus, not present
- avail = false;
- }
- }
- else
- {
- // Didn't find attribute, thus, not present
- avail = false;
- }
-
- return avail;
-}
class I2CTest: public CxxTest::TestSuite
{
@@ -296,28 +270,21 @@ class I2CTest: public CxxTest::TestSuite
break;
default:
- TS_FAIL( "Invalid Chip type specificed in testData!" );
+ TS_FAIL( "testI2CDirect - Invalid Chip type "
+ "specificed in testData!" );
fails++;
continue;
break;
};
- // Check to see if I2C function is there
- if( !isI2CAvailable( theTarget ) )
- {
- TRACFCOMP( g_trac_i2c,
- "testI2CDirect Operation - no i2c function" );
- continue;
- }
-
- // check to see if the target is functional before we
+ // Check to see if the target is functional before we
// continue..
if
(!theTarget->getAttr<TARGETING::ATTR_HWAS_STATE>().functional)
{
TRACFCOMP( g_trac_i2c,
- "testI2CDirect Operation - target not functional");
+ "testI2CDirect - target not functional");
continue;
}
@@ -363,7 +330,7 @@ class I2CTest: public CxxTest::TestSuite
} while( 0 );
TRACFCOMP( g_trac_i2c,
- "testI2CDirect - %d/%d fails",
+ "testI2CDirect - End: %d/%d fails",
fails, cmds );
}
@@ -494,29 +461,22 @@ class I2CTest: public CxxTest::TestSuite
break;
default:
- TS_FAIL( "Invalid Chip type specificed in testData!" );
+ TS_FAIL( "testI2COffset - Invalid Chip type "
+ "specificed in testData!" );
fails++;
continue;
break;
};
- // Check to see if I2C function is there
- if( !isI2CAvailable( theTarget ) )
- {
- TRACFCOMP( g_trac_i2c,
- "testI2COfset Operation - no i2c function" );
- continue;
- }
-
- // check to see if the target is functional before we
+ // Check to see if the target is functional before we
// continue..
if
(!theTarget->getAttr<TARGETING::ATTR_HWAS_STATE>().functional)
{
TRACFCOMP( g_trac_i2c,
- "testI2COffset Operation - target not functional");
+ "testI2COffset - target not functional");
continue;
}
@@ -603,7 +563,8 @@ class I2CTest: public CxxTest::TestSuite
"Data Compare Fail: wrote=%016llx, "
"read back=%016llx. cmd: %d/%d (%d)",
testData[i].data, data, i, NUM_CMDS, j);
- TS_FAIL( "testI2COffset - Failure comparing new data!" );
+ TS_FAIL( "testI2COffset - Failure comparing "
+ "new data!" );
fails++;
// Don't break - try to write back original data
@@ -626,7 +587,8 @@ class I2CTest: public CxxTest::TestSuite
"Data Compare Fail: original=%016llx, "
"read back=%016llx. cmd: %d/%d (%d)",
original_data, data, i, NUM_CMDS, j);
- TS_FAIL( "testI2COffset - Failure comparing original data!" );
+ TS_FAIL( "testI2COffset - Failure comparing "
+ "original data!" );
fails++;
// Break: stop testing if we can't write back
@@ -642,11 +604,41 @@ class I2CTest: public CxxTest::TestSuite
} while( 0 );
TRACFCOMP( g_trac_i2c,
- "testI2COffset - %d/%d fails",
+ "testI2COffset - End: %d/%d fails",
fails, cmds );
}
+ /**
+ * @brief Call I2C Setup Masters Function
+ * This function is part of the shutdown path and is
+ * needed by PHYP to ensure that the I2C masters are
+ * setup correctly on the system.
+ */
+ void testI2CSetupMasters ( void )
+ {
+ errlHndl_t err = NULL;
+ int fails = 0;
+ const int NUM_CMDS = 1;
+
+ TRACFCOMP( g_trac_i2c,
+ "testI2CSetupMasters - Start" );
+
+ err = I2C::i2cSetupMasters();
+
+ if( err )
+ {
+ TS_FAIL( "testI2CSetupMasters - Error returned from "
+ "i2cSetupMasters()");
+ fails++;
+ delete err;
+ }
+
+ TRACFCOMP( g_trac_i2c,
+ "testI2CSetupMasters - End: %d/%d fails",
+ fails, NUM_CMDS );
+ }
+
/**
* @brief I2C Invalid Target test
@@ -678,7 +670,8 @@ class I2CTest: public CxxTest::TestSuite
if( !err )
{
- TS_FAIL( "Failure to return error using Master Sentinel Chip!" );
+ TS_FAIL( "testI2CInvalidTarget - Failure to return error "
+ "using Master Sentinel Chip!" );
fails++;
}
else
@@ -688,7 +681,7 @@ class I2CTest: public CxxTest::TestSuite
}
TRACFCOMP( g_trac_i2c,
- "testI2CInvalidTarget - %d/%d fails",
+ "testI2CInvalidTarget - End: %d/%d fails",
fails, NUM_CMDS );
}
@@ -704,6 +697,9 @@ class I2CTest: public CxxTest::TestSuite
uint64_t data = 0x0ull;
size_t dataSize = 8;
+ TRACFCOMP( g_trac_i2c,
+ "testI2CInvalidOperation - Start" );
+
do
{
// Get a processor Target
@@ -712,15 +708,6 @@ class I2CTest: public CxxTest::TestSuite
tS.masterProcChipTargetHandle( testTarget );
assert(testTarget != NULL);
- // Check to see if I2C function is there
- if( !isI2CAvailable( testTarget ) )
- {
- TRACFCOMP( g_trac_i2c,
- "testI2CInvalid Operation - no i2c function" );
-
-
- continue;
- }
// check to see if the target is functional before we
// continue..
@@ -728,7 +715,7 @@ class I2CTest: public CxxTest::TestSuite
(!testTarget->getAttr<TARGETING::ATTR_HWAS_STATE>().functional)
{
TRACFCOMP( g_trac_i2c,
- "testI2CInvalide Operation - not functional" );
+ "testI2CInvalidOperation - not functional" );
continue;
@@ -746,7 +733,8 @@ class I2CTest: public CxxTest::TestSuite
if( NULL == err )
{
fails++;
- TS_FAIL( "Error should've resulted in Operation type of LAST_OP_TYPE!" );
+ TS_FAIL( "testI2CInvalidOperation - Error should've "
+ "resulted in Operation type of LAST_OP_TYPE!" );
}
else
{
@@ -755,7 +743,7 @@ class I2CTest: public CxxTest::TestSuite
}
} while( 0 );
TRACFCOMP( g_trac_i2c,
- "testI2CInvalidOperation - %d/%d fails",
+ "testI2CInvalidOperation - End: %d/%d fails",
fails, num_ops );
}
OpenPOWER on IntegriCloud