Skip to content

Commit

Permalink
Add MMIO test cases that force failures
Browse files Browse the repository at this point in the history
Change-Id: I9af1230917c1629c9f9568ae6645291c11b0140e
Reviewed-on: http://rchgit01.rchland.ibm.com/gerrit1/78524
Tested-by: Jenkins Server <pfd-jenkins+hostboot@us.ibm.com>
Tested-by: FSP CI Jenkins <fsp-CI-jenkins+hostboot@us.ibm.com>
Tested-by: Jenkins OP Build CI <op-jenkins+hostboot@us.ibm.com>
Tested-by: Jenkins OP HW <op-hw-jenkins+hostboot@us.ibm.com>
Reviewed-by: Matt Derksen <mderkse1@us.ibm.com>
Reviewed-by: Roland Veloz <rveloz@us.ibm.com>
Reviewed-by: Daniel M. Crowell <dcrowell@us.ibm.com>
  • Loading branch information
milesg-github authored and dcrowell77 committed Jun 7, 2019
1 parent 5634271 commit a697687
Show file tree
Hide file tree
Showing 3 changed files with 147 additions and 30 deletions.
8 changes: 8 additions & 0 deletions src/build/simics/standalone.simics
Expand Up @@ -143,6 +143,14 @@ if ($hb_mode == 0) { #Only do this on Axone and later models that have Explorer
$obj->mscc_regs_xcbi_ram1[14] = 0x063EF2EE
$obj->mscc_regs_xcbi_ram1[15] = 0x063B5957
$obj->mscc_regs_xcbi_ram1[16] = 0x40A3A12D

# Allow for testing MMIO HW failures
# Forces write access to TRACE_TRDATA_CONFIG_0 to fail
# in src/usr/mmio/test/mmiotest.H
# NOTE: address is left shifted 3 and has MMIO
# offset (0x100000000) added.
$obj->mmio_regs_mmioerr = 0x0000000140082018

}
}

Expand Down
2 changes: 1 addition & 1 deletion src/usr/mmio/test/makefile
Expand Up @@ -27,7 +27,7 @@ ROOTPATH = ../../../..
MODULE = testmmio

EXTRAINCDIR += ${ROOTPATH}/src/import/chips/ocmb/explorer/common/include/

EXTRAINCDIR += ${ROOTPATH}/src/import/chips/common/

TESTS = *.H

Expand Down
167 changes: 138 additions & 29 deletions src/usr/mmio/test/mmiotest.H
Expand Up @@ -31,79 +31,188 @@
#include <targeting/common/utilFilter.H>
#include <explorer_scom_addresses.H>
#include <exp_oc_regs.H>
#include <sys/mmio.h>
#include <utils/chipids.H>

#define SCOM2MMIO_ADDR(_ADDR) (EXPLR_IB_MMIO_OFFSET | (_ADDR << 3))
#define CNFG2MMIO_ADDR(_ADDR) (EXPLR_IB_CONFIG_OFFSET | _ADDR)
#define BYTESWAP64(_DATA) (__builtin_bswap64(_DATA))

static const uint64_t EXPLR_IB_CONFIG_OFFSET = 0x0000000000000000ull;
static const uint64_t EXPLR_IB_MMIO_OFFSET = 0x0000000100000000ull; // 4GB

// NOTE: changing this address requires changes
// to src/build/simics/standalone.simics
static const uint64_t EXPLR_INVALID_SCOM_ADDR =
EXPLR_TP_MB_UNIT_TOP_TRACE_TRDATA_CONFIG_0;


class MmioTest : public CxxTest::TestSuite
{
public:

/**
* @brief Test valid MMIO calls
* @brief Test MMIO calls
*/
void test_Valid(void)
void testExplrMMIO(void)
{
TS_TRACE("MmioTest::test_Valid> Start" );
TS_INFO("testExplrMMIO> Start" );

uint64_t fails = 0;
uint64_t total = 0;
errlHndl_t l_err = nullptr;
uint32_t regdata4 = 0;
size_t op_size = 0;
uint64_t l_buffer64;

// Get OCMB target, return if there is no OCMB
TARGETING::TargetHandle_t ocmb_target = nullptr;
TARGETING::TargetHandle_t explr_target = nullptr;
TARGETING::TargetHandleList ocmb_target_list;
TARGETING::getAllChips(ocmb_target_list, TARGETING::TYPE_OCMB_CHIP);
if (ocmb_target_list.size() == 0)
{
TS_TRACE("MmioTest::test_Valid> Target is NULL");
TS_INFO("MmioTest::test_Valid> Target is NULL");
TS_INFO("testExplrMMIO> No OCMB targets found. Exiting.");
return;
}
explr_target = ocmb_target_list[0];
if(explr_target->getAttr<TARGETING::ATTR_CHIP_ID>() !=
POWER_CHIPID::EXPLORER_16)
{
TS_INFO("testExplrMMIO> No explorer targets found. Exiting.");
return;
}
ocmb_target = ocmb_target_list[0];

// valid read from config space register
++total;
op_size = sizeof(regdata4);
l_err = DeviceFW::deviceRead(
ocmb_target,
explr_target,
&regdata4,
op_size,
DEVICE_MMIO_ADDRESS((EXPLR_IB_CONFIG_OFFSET |
EXPLR_OC_O0MBIT_O0DID_LSB),
op_size));
DEVICE_MMIO_ADDRESS(
CNFG2MMIO_ADDR(EXPLR_OC_O0MBIT_O0DID_LSB),
op_size));
if(l_err != nullptr)
{
TS_TRACE("MmioTest::test_Valid> Error for read, RC=0x%04X",
ERRL_GETRC_SAFE(l_err));
TS_FAIL("MmioTest::test_Valid> Error for read, RC=0x%04X",
ERRL_GETRC_SAFE(l_err));
++fails;
errlCommit(l_err, CXXTEST_COMP_ID);
TS_FAIL("testExplrMMIO> Error for config read, RC=0x%04X",
ERRL_GETRC_SAFE(l_err));
}

// valid write to config space register
++total;
op_size = sizeof(regdata4);
l_err = DeviceFW::deviceWrite(
ocmb_target,
explr_target,
&regdata4,
op_size,
DEVICE_MMIO_ADDRESS((EXPLR_IB_CONFIG_OFFSET |
EXPLR_OC_O0CCD_LSB),
op_size));
DEVICE_MMIO_ADDRESS(
CNFG2MMIO_ADDR(EXPLR_OC_O0CCD_LSB),
op_size));
if(l_err != nullptr)
{
errlCommit(l_err, CXXTEST_COMP_ID);
TS_FAIL("testExplrMMIO> Error for config write, RC=0x%04X",
ERRL_GETRC_SAFE(l_err));
}

// 1st valid write to SCOM register (also sets up
// tests for forcing HW read/write failures)
// Set the PCB error bits (8:10) to binary 100, which means
// 'invalid address'
// NOTE: must byteswap to little endian before writing
uint64_t GIF2PCB_INVALID_SCOM_ADDR_ERROR = 0x0080000000000000ull;
l_buffer64 = BYTESWAP64(GIF2PCB_INVALID_SCOM_ADDR_ERROR);
op_size = sizeof(l_buffer64);
l_err = DeviceFW::deviceWrite(
explr_target,
&l_buffer64,
op_size,
DEVICE_MMIO_ADDRESS(
SCOM2MMIO_ADDR(
EXPLR_TP_MB_UNIT_TOP_GIF2PCB_ERROR_REG),
op_size));
if(l_err != nullptr)
{
errlCommit(l_err, CXXTEST_COMP_ID);
TS_FAIL("testExplrMMIO> Error for gif2pcb write, RC=0x%04X",
ERRL_GETRC_SAFE(l_err));
return;
}

// 2nd valid write to SCOM register (also sets up
// tests for forcing HW read/write failures)
// This register should contain a copy of the GIF2PCB error register
// starting at bit 32
// NOTE: must byteswap to little endian before writing data
uint64_t PIB2GIF_INVALID_SCOM_ADDR_ERROR =
0x0000000000000000ull |
((GIF2PCB_INVALID_SCOM_ADDR_ERROR &
0xffffc00000000000ull) >> 32);
l_buffer64 = BYTESWAP64(PIB2GIF_INVALID_SCOM_ADDR_ERROR);
op_size = sizeof(l_buffer64);
l_err = DeviceFW::deviceWrite(
explr_target,
&l_buffer64,
op_size,
DEVICE_MMIO_ADDRESS(
SCOM2MMIO_ADDR(
EXPLR_TP_MB_UNIT_TOP_PIB2GIF_ERROR_REG),
op_size));

if(l_err != nullptr)
{
TS_TRACE("MmioTest::test_Valid> Error for write, RC=0x%04X",
ERRL_GETRC_SAFE(l_err));
TS_FAIL("MmioTest::test_Valid> Error for write, RC=0x%04X",
errlCommit(l_err, CXXTEST_COMP_ID);
TS_FAIL("testExplrMMIO> Error for pib2gif write, RC=0x%04X",
ERRL_GETRC_SAFE(l_err));
++fails;
return;
}

// Write to an "invalid" scom address. Should
// return with failure (now that we've set up the error regs).
// NOTE: Also, writing MMIO_OCMB_UE_DETECTED to this register
// sets up the following read to the same register
// to fail.
l_buffer64 = MMIO_OCMB_UE_DETECTED;
op_size = sizeof(l_buffer64);
l_err = DeviceFW::deviceWrite(
explr_target,
&l_buffer64,
op_size,
DEVICE_MMIO_ADDRESS(
SCOM2MMIO_ADDR(EXPLR_INVALID_SCOM_ADDR),
op_size));

if(l_err == nullptr)
{
TS_FAIL("testExplrMMIO> "
"did not recieve expected failure on mmio write");
return;
}
else
{
TS_INFO("testExplrMMIO> recieved expected failure on mmio write");
errlCommit(l_err, CXXTEST_COMP_ID);
}

TS_TRACE("Mmio::test_Valid> %d/%d fails", fails, total);
// Read from an "invalid" scom address. Should
// return with failure (now that we've se up the error regs).
op_size = sizeof(l_buffer64);
l_err = DeviceFW::deviceRead(
explr_target,
&l_buffer64,
op_size,
DEVICE_MMIO_ADDRESS(
SCOM2MMIO_ADDR(EXPLR_INVALID_SCOM_ADDR),
op_size));
if(l_err == nullptr)
{
TS_INFO("testExplrMMIO> data read from invalid address: 0x%016llx",
l_buffer64);
TS_FAIL("testExplrMMIO> "
"did not recieve expected failure on mmio read");
}
else
{
TS_INFO("testExplrMMIO> recieved expected failure on mmio read");
errlCommit(l_err, CXXTEST_COMP_ID);
}
TS_INFO("testExplrMMIO> Done");
};
};

0 comments on commit a697687

Please sign in to comment.