Skip to content

Commit

Permalink
Add asserts for invalid states of enterprise & half dimm mode
Browse files Browse the repository at this point in the history
Change-Id: I995c333fc7f891ea7fa055097d4377a861a1e391
Reviewed-on: http://rchgit01.rchland.ibm.com/gerrit1/87345
Tested-by: FSP CI Jenkins <fsp-CI-jenkins+hostboot@us.ibm.com>
Tested-by: Jenkins Server <pfd-jenkins+hostboot@us.ibm.com>
Tested-by: PPE CI <ppe-ci+hostboot@us.ibm.com>
Reviewed-by: Louis Stermole <stermole@us.ibm.com>
Reviewed-by: STEPHEN GLANCY <sglancy@us.ibm.com>
Dev-Ready: STEPHEN GLANCY <sglancy@us.ibm.com>
Tested-by: Hostboot CI <hostboot-ci+hostboot@us.ibm.com>
Reviewed-by: Jennifer A Stofer <stofer@us.ibm.com>
Reviewed-on: http://rchgit01.rchland.ibm.com/gerrit1/87600
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: Daniel M Crowell <dcrowell@us.ibm.com>
  • Loading branch information
markypizz authored and dcrowell77 committed Dec 5, 2019
1 parent ef6600c commit ecac819
Show file tree
Hide file tree
Showing 9 changed files with 318 additions and 101 deletions.
23 changes: 10 additions & 13 deletions src/import/chips/ocmb/explorer/procedures/hwp/memory/exp_getecid.C
Expand Up @@ -40,6 +40,7 @@
#include <explorer_scom_addresses_fld.H>
#include <mss_explorer_attribute_setters.H>
#include <generic/memory/mss_git_data_helper.H>
#include <lib/plug_rules/exp_plug_rules.H>

extern "C"
{
Expand All @@ -53,24 +54,20 @@ extern "C"
{
mss::display_git_commit_info("exp_getecid");

// Using FUSE enterprise_dis bit, determine whether enterprise is disabled, otherwise
// we will enable it. Override to disable it is done in omi_setup. Half_dimm_mode we
// will also disable by default, as it is not a feature of P systems
{
uint8_t l_enterprise_mode = fapi2::ENUM_ATTR_MSS_OCMB_ENTERPRISE_MODE_NON_ENTERPRISE; // 0
uint8_t l_half_dimm_mode = fapi2::ENUM_ATTR_MSS_OCMB_HALF_DIMM_MODE_FULL_DIMM; // 0
bool l_enterprise_fuse = false;
bool l_enterprise_final = false;

FAPI_TRY(mss::exp::ecid::get_enterprise_and_half_dimm_from_fuse(
i_target, l_enterprise_mode, l_half_dimm_mode),
"exp_getecid: getting enterprise and half_dimm from fuse failed on %s",
FAPI_TRY(mss::exp::ecid::get_enterprise_from_fuse(i_target, l_enterprise_fuse),
"exp_getecid: getting enterprise from fuse failed on %s",
mss::c_str(i_target));

// Set attributes
FAPI_TRY(mss::attr::set_ocmb_enterprise_mode(i_target, l_enterprise_mode),
"exp_getecid: Could not set ATTR_MSS_OCMB_ENTERPRISE_MODE");
// Calculate the global enterprise mode state while verifying plug rules with policy and override attributes
FAPI_TRY(mss::exp::plug_rule::enterprise_mode(i_target, l_enterprise_fuse, l_enterprise_final));

FAPI_TRY(mss::attr::set_ocmb_half_dimm_mode(i_target, l_half_dimm_mode),
"exp_getecid: Could not set ATTR_MSS_OCMB_HALF_DIMM_MODE");
// Set global enterprise mode attribute
FAPI_TRY(mss::attr::set_ocmb_enterprise_mode(i_target, l_enterprise_final),
"exp_getecid: Could not set ATTR_MSS_OCMB_ENTERPRISE_MODE");
}

//
Expand Down
Expand Up @@ -92,12 +92,15 @@ extern "C"
fapi2::buffer<uint64_t> l_dlx_config1_data;

uint8_t l_edpl_disable = 0;
bool l_is_enterprise = false;
uint8_t l_enterprise_attr = 0;
bool l_is_half_dimm = false;
bool l_is_enterprise = false;

// Gets the configuration information from attributes
FAPI_TRY(mss::enterprise_mode(i_target, l_is_enterprise));
FAPI_TRY(mss::half_dimm_mode(i_target, l_is_half_dimm));
FAPI_TRY(mss::attr::get_ocmb_enterprise_mode(i_target, l_enterprise_attr));
l_is_enterprise = (l_enterprise_attr == fapi2::ENUM_ATTR_MSS_OCMB_ENTERPRISE_MODE_ENTERPRISE);

FAPI_TRY(mss::half_dimm_mode(i_target, l_is_enterprise, l_is_half_dimm));
FAPI_TRY(mss::attr::get_mss_omi_edpl_disable(l_edpl_disable));

// Prints out the data
Expand Down
Expand Up @@ -48,40 +48,72 @@ namespace mss
{

///
/// @brief Gets whether the OCMB will be configred to enterprise mode
/// @param[in] i_target OCMB target on which to operate
/// @param[out] o_is_enterprise_mode true if the part is in enterprise mode
/// @return fapi2::ReturnCode - FAPI2_RC_SUCCESS iff get is OK
/// @brief Unit-testable half dimm mode helper function. Calculates half dimm mode based on input params
/// @param[in] i_target OCMB chip
/// @param[in] i_is_enterprise enterprise mode is enabled
/// @param[in] i_half_dimm_attr half dimm mode as obtained from attribute
/// @param[in] i_half_dimm_override_attr half dimm mode override from attribute
/// @param[out] o_is_half_dimm_mode resulting value for half dimm mode after calculations
/// @return fapi2::ReturnCode FAPI2_RC_SUCCESS iff success, else error code
///
inline fapi2::ReturnCode enterprise_mode( const fapi2::Target<fapi2::TARGET_TYPE_OCMB_CHIP>&
i_target,
bool& o_is_enterprise_mode )
inline fapi2::ReturnCode half_dimm_mode_helper(
const fapi2::Target<fapi2::TARGET_TYPE_OCMB_CHIP>& i_target,
const bool i_is_enterprise,
const uint8_t i_half_dimm_attr,
const uint8_t i_half_dimm_override_attr,
bool& o_is_half_dimm_mode )
{
// Constexprs for beautification
constexpr uint8_t ENTERPRISE = fapi2::ENUM_ATTR_MSS_OCMB_ENTERPRISE_MODE_ENTERPRISE;
constexpr uint8_t NO_OVERRIDE = fapi2::ENUM_ATTR_MSS_OCMB_NONENTERPRISE_MODE_OVERRIDE_NO_OVERRIDE;
o_is_half_dimm_mode = false;

// Variables
o_is_enterprise_mode = false;
uint8_t l_enterprise = 0;
uint8_t l_override = 0;
bool l_is_half_dimm = 0;

// First let's assert that ocmb_half_dimm_mode isn't HALF_DIMM when ENTERPRISE is 0
// Even though this could theoretically be overridden back to FULL_DIMM, we should
// check that the initial value is also valid.
FAPI_ASSERT(!i_half_dimm_attr || i_is_enterprise,
fapi2::MSS_EXP_HALF_DIMM_MODE_NOT_SUPPORTED()
.set_ENTERPRISE_SETTING(i_is_enterprise)
.set_HALF_DIMM_SETTING(i_half_dimm_attr)
.set_OCMB_TARGET(i_target),
"%s Invalid configuration: ATTR_MSS_OCMB_HALF_DIMM_MODE set to HALF_DIMM while enterprise is disabled",
mss::c_str(i_target));

FAPI_TRY( mss::attr::get_ocmb_enterprise_mode(i_target, l_enterprise) );
FAPI_TRY( mss::attr::get_ocmb_nonenterprise_mode_override(i_target, l_override) );
// This might be overwritten below by overrides
l_is_half_dimm = (i_half_dimm_attr == fapi2::ENUM_ATTR_MSS_OCMB_HALF_DIMM_MODE_HALF_DIMM);

// Now let's apply the override
if (i_half_dimm_override_attr == fapi2::ENUM_ATTR_MSS_OCMB_HALF_DIMM_MODE_OVERRIDE_OVERRIDE_HALF_DIMM)
{
const bool l_enterprise_mode = l_enterprise == ENTERPRISE;
const bool l_no_override = l_override == NO_OVERRIDE;
// We will be in enterprise mode (true) IF
// 1) the chip is in enterprise mode (we can't run in enterprise mode if the part is non-enterprise capable) AND
// 2) we do not have the override to non-enterprise mode
o_is_enterprise_mode = l_enterprise_mode && l_no_override;

FAPI_INF("%s is in %s mode. (OCMB chip is %s, with %s)", mss::c_str(i_target),
o_is_enterprise_mode ? "enterprise" : "non-enterprise", l_enterprise_mode ? "enterprise" : "non-enterprise",
l_no_override ? "no override" : "override to non-enterprise");
l_is_half_dimm = true;

// Assert once more that this is valid
FAPI_ASSERT(!l_is_half_dimm || i_is_enterprise,
fapi2::MSS_EXP_HALF_DIMM_MODE_NOT_SUPPORTED()
.set_ENTERPRISE_SETTING(i_is_enterprise)
.set_HALF_DIMM_SETTING(l_is_half_dimm)
.set_OCMB_TARGET(i_target),
"%s Invalid configuration: HALF_DIMM_MODE overridden to HALF_DIMM while enterprise is disabled",
mss::c_str(i_target));

FAPI_DBG("%s overridden to HALF_DIMM_MODE", mss::c_str(i_target));
}

else if (i_half_dimm_override_attr == fapi2::ENUM_ATTR_MSS_OCMB_HALF_DIMM_MODE_OVERRIDE_OVERRIDE_FULL_DIMM)
{
l_is_half_dimm = false;
FAPI_DBG("%s overridden to FULL_DIMM_MODE", mss::c_str(i_target));
}

o_is_half_dimm_mode = l_is_half_dimm;

FAPI_INF("%s %s in enterprise mode, and %s override is present. The chip is in %s (attribute %u)",
mss::c_str(i_target),
i_is_enterprise ? "is" : "is not",
i_half_dimm_override_attr > 0 ? "an" : "no",
o_is_half_dimm_mode ? "half-DIMM mode" : "full-DIMM mode", l_is_half_dimm);

return fapi2::FAPI2_RC_SUCCESS;

fapi_try_exit:
return fapi2::current_err;
}
Expand All @@ -92,45 +124,22 @@ fapi_try_exit:
/// @param[out] o_is_half_dimm_mode true if the part is in half-DIMM mode
/// @return fapi2::ReturnCode - FAPI2_RC_SUCCESS iff get is OK
///
inline fapi2::ReturnCode half_dimm_mode( const fapi2::Target<fapi2::TARGET_TYPE_OCMB_CHIP>&
i_target,
bool& o_is_half_dimm_mode )
inline fapi2::ReturnCode half_dimm_mode(
const fapi2::Target<fapi2::TARGET_TYPE_OCMB_CHIP>& i_target,
const bool i_is_enterprise_mode,
bool& o_is_half_dimm_mode )
{
// Variables
o_is_half_dimm_mode = false;
bool l_is_enterprise = false;
uint8_t l_half_dimm = 0;
uint8_t l_override = 0;

FAPI_TRY( enterprise_mode(i_target, l_is_enterprise) );

// We're in full DIMM mode if we're in non-enterprise mode
if(!l_is_enterprise)
{
o_is_half_dimm_mode = false;
FAPI_INF("%s is in full-DIMM since the chip is in non-enterprise mode", mss::c_str(i_target));
return fapi2::FAPI2_RC_SUCCESS;
}

// Now that we're not in enterprise mode, check for overrides
FAPI_TRY( mss::attr::get_ocmb_half_dimm_mode_override(i_target, l_override) );

// If we have an override, set based upon the override
if(l_override != fapi2::ENUM_ATTR_MSS_OCMB_HALF_DIMM_MODE_OVERRIDE_NO_OVERRIDE)
{
o_is_half_dimm_mode = l_override == fapi2::ENUM_ATTR_MSS_OCMB_HALF_DIMM_MODE_OVERRIDE_OVERRIDE_HALF_DIMM;
FAPI_INF("%s is in enterprise mode, and %s override is present. The chip is in %s (attribute %u)", mss::c_str(i_target),
"an", o_is_half_dimm_mode ? "half-DIMM mode" : "full-DIMM mode", l_override);
return fapi2::FAPI2_RC_SUCCESS;
}
uint8_t l_half_dimm_attr = 0;
uint8_t l_override_attr = 0;

// No override, so go with the attribute derived from the ECID
FAPI_TRY( mss::attr::get_ocmb_half_dimm_mode(i_target, l_half_dimm) );
FAPI_TRY( mss::attr::get_ocmb_half_dimm_mode(i_target, l_half_dimm_attr) );
FAPI_TRY( mss::attr::get_ocmb_half_dimm_mode_override(i_target, l_override_attr) );

// Set half DIMM mode based upon the the normal attribute
o_is_half_dimm_mode = l_half_dimm == fapi2::ENUM_ATTR_MSS_OCMB_HALF_DIMM_MODE_HALF_DIMM;
FAPI_INF("%s is in enterprise mode, and %s override is present. The chip is in %s (attribute %u)", mss::c_str(i_target),
"no", o_is_half_dimm_mode ? "half-DIMM mode" : "full-DIMM mode", l_half_dimm);
// o_is_half_dimm_mode will be set by the helper function
FAPI_TRY( mss::half_dimm_mode_helper(i_target, i_is_enterprise_mode, l_half_dimm_attr, l_override_attr,
o_is_half_dimm_mode));

fapi_try_exit:
return fapi2::current_err;
Expand Down
Expand Up @@ -50,32 +50,21 @@ namespace ecid
{

///
/// @brief Determines enterprise and half dimm states from explorer FUSE
/// @brief Determines enterprise state from explorer FUSE
/// @param[in] i_target the controller
/// @param[out] o_enterprise_mode state
/// @param[out] o_half_dimm_mode state
/// @return FAPI2_RC_SUCCESS iff ok
///
fapi2::ReturnCode get_enterprise_and_half_dimm_from_fuse(
fapi2::ReturnCode get_enterprise_from_fuse(
const fapi2::Target<fapi2::TARGET_TYPE_OCMB_CHIP>& i_target,
uint8_t& o_enterprise_mode,
uint8_t& o_half_dimm_mode)
bool& o_enterprise_mode)
{
fapi2::buffer<uint64_t> l_reg_resp_buffer;
FAPI_TRY(fapi2::getScom( i_target, static_cast<uint64_t>(EXPLR_EFUSE_IMAGE_OUT_0), l_reg_resp_buffer ),
"exp_getecid: could not read explorer fuse register 0x%08x", EXPLR_EFUSE_IMAGE_OUT_0);

// Default to disabled
o_enterprise_mode = fapi2::ENUM_ATTR_MSS_OCMB_ENTERPRISE_MODE_NON_ENTERPRISE; // 0

// If we support enterprise mode, enable it until otherwise overridden in OMI_SETUP
if(!l_reg_resp_buffer.getBit <EXPLR_EFUSE_IMAGE_OUT_0_ENTERPRISE_MODE_DIS> ())
{
o_enterprise_mode = fapi2::ENUM_ATTR_MSS_OCMB_ENTERPRISE_MODE_ENTERPRISE; // 1, enabled
}

// half_dimm_mode will remain disabled for P systems
o_half_dimm_mode = fapi2::ENUM_ATTR_MSS_OCMB_HALF_DIMM_MODE_FULL_DIMM; // 0, disabled
// Since the bit is a disable bit, take the opposite to get enable=true, disable=false
o_enterprise_mode = !(l_reg_resp_buffer.getBit<EXPLR_EFUSE_IMAGE_OUT_0_ENTERPRISE_MODE_DIS>());

fapi_try_exit:
return fapi2::current_err;
Expand Down
Expand Up @@ -47,16 +47,14 @@ namespace ecid
{

///
/// @brief Determines enterprise and half dimm states from explorer FUSE
/// @brief Determines enterprise state from explorer FUSE
/// @param[in] i_target the controller
/// @param[out] o_enterprise_mode state
/// @param[out] o_half_dimm_mode state
/// @return FAPI2_RC_SUCCESS iff ok
///
fapi2::ReturnCode get_enterprise_and_half_dimm_from_fuse(
fapi2::ReturnCode get_enterprise_from_fuse(
const fapi2::Target<fapi2::TARGET_TYPE_OCMB_CHIP>& i_target,
uint8_t& o_enterprise_mode,
uint8_t& o_half_dimm_mode);
bool& o_enterprise_mode);

///
/// @brief Reads ECID into output array from fuse
Expand Down

0 comments on commit ecac819

Please sign in to comment.