diff options
Diffstat (limited to 'src')
-rw-r--r-- | src/include/usr/devicefw/driverif.H | 11 | ||||
-rw-r--r-- | src/include/usr/expscom/expscom_reasoncodes.H | 48 | ||||
-rw-r--r-- | src/include/usr/hbotcompid.H | 10 | ||||
-rw-r--r-- | src/makefile | 1 | ||||
-rw-r--r-- | src/usr/expscom/README.md | 141 | ||||
-rw-r--r-- | src/usr/expscom/expscomtrace.C | 38 | ||||
-rw-r--r-- | src/usr/expscom/expscomtrace.H | 39 | ||||
-rw-r--r-- | src/usr/expscom/i2cscomdd.C | 369 | ||||
-rw-r--r-- | src/usr/expscom/i2cscomdd.H | 67 | ||||
-rw-r--r-- | src/usr/expscom/makefile | 42 | ||||
-rwxr-xr-x | src/usr/fapi2/fapi2.mk | 4 | ||||
-rw-r--r-- | src/usr/initservice/extinitsvc/extinitsvctasks.H | 12 | ||||
-rw-r--r-- | src/usr/makefile | 65 | ||||
-rw-r--r-- | src/usr/scom/scom.C | 23 | ||||
-rw-r--r-- | src/usr/targeting/common/Targets.pm | 1 | ||||
-rwxr-xr-x | src/usr/targeting/common/processMrw.pl | 1 | ||||
-rw-r--r-- | src/usr/targeting/common/xmltohb/attribute_types.xml | 12 | ||||
-rw-r--r-- | src/usr/targeting/common/xmltohb/target_types.xml | 33 |
18 files changed, 879 insertions, 38 deletions
diff --git a/src/include/usr/devicefw/driverif.H b/src/include/usr/devicefw/driverif.H index df90800b3..9bed7bb94 100644 --- a/src/include/usr/devicefw/driverif.H +++ b/src/include/usr/devicefw/driverif.H @@ -5,7 +5,7 @@ /* */ /* OpenPOWER HostBoot Project */ /* */ -/* Contributors Listed Below - COPYRIGHT 2011,2017 */ +/* Contributors Listed Below - COPYRIGHT 2011,2018 */ /* [+] International Business Machines Corp. */ /* */ /* */ @@ -56,7 +56,7 @@ namespace DeviceFW HOSTI2C, FSI_I2C, SBEFIFOSCOM, - + I2CSCOM, LAST_DRIVER_ACCESS_TYPE }; @@ -109,6 +109,13 @@ namespace DeviceFW #define DEVICE_IBSCOM_ADDRESS(i_address) \ DeviceFW::IBSCOM, static_cast<uint64_t>((i_address)) + /** Construct the device addressing parameters for I2CSCOM (i2c scom) + * device ops. + * @param[in] i_address - I2CSCOM address to operate on. + */ + #define DEVICE_I2CSCOM_ADDRESS(i_address) \ + DeviceFW::I2CSCOM, static_cast<uint64_t>((i_address)) + /** * @brief Macro that handles the I2C parameters */ diff --git a/src/include/usr/expscom/expscom_reasoncodes.H b/src/include/usr/expscom/expscom_reasoncodes.H new file mode 100644 index 000000000..62713531c --- /dev/null +++ b/src/include/usr/expscom/expscom_reasoncodes.H @@ -0,0 +1,48 @@ +/* IBM_PROLOG_BEGIN_TAG */ +/* This is an automatically generated prolog. */ +/* */ +/* $Source: src/include/usr/expscom/expscom_reasoncodes.H $ */ +/* */ +/* OpenPOWER HostBoot Project */ +/* */ +/* Contributors Listed Below - COPYRIGHT 2011,2018 */ +/* [+] International Business Machines Corp. */ +/* */ +/* */ +/* Licensed under the Apache License, Version 2.0 (the "License"); */ +/* you may not use this file except in compliance with the License. */ +/* You may obtain a copy of the License at */ +/* */ +/* http://www.apache.org/licenses/LICENSE-2.0 */ +/* */ +/* Unless required by applicable law or agreed to in writing, software */ +/* distributed under the License is distributed on an "AS IS" BASIS, */ +/* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or */ +/* implied. See the License for the specific language governing */ +/* permissions and limitations under the License. */ +/* */ +/* IBM_PROLOG_END_TAG */ +#ifndef __EXPSCOM_REASONCODES_H +#define __EXPSCOM_REASONCODES_H + +#include <hbotcompid.H> + +namespace EXPSCOM +{ + enum EXPSCOMModuleId + { + MOD_OCMBSCOM_INVALID = 0x00, // Zero is an invalid module id + MOD_I2CSCOM_PERFORM_OP = 0x01, // i2cscom.C : i2cScomPerformOp + }; + + enum EXPSCOMReasonCode + { + RC_INVALID = EXPSCOM_COMP_ID | 0x00, + RC_INVALID_LENGTH = EXPSCOM_COMP_ID | 0x01, + RC_INVALID_MODEL_TYPE = EXPSCOM_COMP_ID | 0x02, + RC_INVALID_OPTYPE = EXPSCOM_COMP_ID | 0x03, + RC_INVALID_ADDRESS = EXPSCOM_COMP_ID | 0x04, + }; +}; + +#endif diff --git a/src/include/usr/hbotcompid.H b/src/include/usr/hbotcompid.H index 6405d0a89..4db19e164 100644 --- a/src/include/usr/hbotcompid.H +++ b/src/include/usr/hbotcompid.H @@ -445,6 +445,14 @@ const compId_t NVDIMM_COMP_ID = 0x3500; const char NVDIMM_COMP_NAME[] = "nvdimm"; //@} +/** @name EXPSCOM + * Explorer OCMB Scom DDs (MMIO and I2C explorer scom drivers) + */ +//@{ +const compId_t EXPSCOM_COMP_ID = 0x3600; +const char EXPSCOM_COMP_NAME[] = "expscom"; +//@} + /** @name NVRAM * NVRAM Support component */ @@ -461,7 +469,7 @@ const char NVRAM_COMP_NAME[] = "nvram"; //@{ const compId_t HDAT_COMP_ID = 0x9000; const char HDAT_COMP_NAME[] = "hdat"; - +//@} /** @name PRDF * PRDF component diff --git a/src/makefile b/src/makefile index d4a22f2df..9c82b0035 100644 --- a/src/makefile +++ b/src/makefile @@ -214,6 +214,7 @@ EXTENDED_MODULES += $(if $(CONFIG_NVDIMM),nvdimm) EXTENDED_MODULES += $(if $(CONFIG_FSP_BUILD),,nvram) EXTENDED_MODULES += mmio EXTENDED_MODULES += smf +EXTENDED_MODULES += expscom #*************************************** # Working test modules diff --git a/src/usr/expscom/README.md b/src/usr/expscom/README.md new file mode 100644 index 000000000..d6d7a8284 --- /dev/null +++ b/src/usr/expscom/README.md @@ -0,0 +1,141 @@ +## Overall Description +The expscom module contains Hostboots device drivers to communicate with scom regs +on the Explorer Open-Capi Memory Buffer (OCMB) chip. Initially when Hostboot starts +the SCOM_SWITCHES attribute on all OCMB chips will be set such that useI2cScom field +is 1 and all other fields are 0. After OMI 's are trained the SCOM_SWITCHES attribute +on the OCMB targets will change so that the useIbScom field will be set to 1 and +all other fields will be 0. + +### Explorer I2C SCOM + +When the useI2cScom field is set in SCOM_SWITCHES this is how the +fapi2::getScom API for OCMB targets will be processed (lets say for now this is IBM scom address): + +* Generic FAPI2 getScom API that will be called in a hardware procedure (HWP) + + + fapi2::getScom(myOcmbTarget, scomAddr, io_buffer); +* Platform Specifc FAPI2 getScom API which the generic wrapper immediately calls + + + fapi2::platGetScom(myOcmbTarget, scomAddr, io_buffer); +* Platform Specifc FAPI2 getScom API resolves to calling into Hostboot's device framework to whatever +function is registered to read OCMB target for DeviceFW::SCOM operations + + + DeviceFW::deviceRead(myOcmbTarget, io_buffer, + sizeof(uint64_t), DeviceFW::SCOM, + scomAddr, READ) +* scomPeformOp is what is defined to handle DeviceFW::SCOM operations to the OCMB chip targets + + + SCOM::scomPerformOp(READ, myOCMBTarget, io_buffer, + sizeof(uint64_t), DeviceFW::SCOM, + scomAddr) +* scomPeformOp is basically a wrapper for checkIndirectAndDoScom There are no indirect scoms for +OCMB target scoms so we will end up calling doScomOp + + + checkIndirectAndDoScom(READ, myOCMBTarget, io_buffer, + sizeof(uint64_t), DeviceFW::SCOM, + scomAddr) + +* doScomOp looks at the SCOM_SWITCHES attribute and decides which type of scom to do for the given target. + + + doScomOp(READ, myOCMBTarget, io_buffer, + sizeof(uint64_t), DeviceFW::SCOM, + scomAddr) + +* If the useI2cScom field is set to 1 then we will call the function that is registered to i2c scoms for OCMB targets + + + deviceOp(READ, myOCMBTarget, io_buffer, + sizeof(uint64_t), DeviceFW::I2CSCOM, + scomAddr) + +* i2cScomPerformOp is the function that is registered to handle i2cScom operations, +this function will perform some simple param validation before deciding whether to +call the getScom or putScom depending if the op is READ or WRITE respectively + + + i2cScomPerformOp(READ, myOCMBTarget, io_buffer, + sizeof(uint64_t), DeviceFW::I2CSCOM, + scomAddr) + +* The base device drivers are defined as EKB HWPs so we must run FAPI_EXEC_HWP in order to correctly call the i2c_get_scom hwp\ +**Note: that EXEC and not INVOKE is used because it is likely this path +will be called within other HWPs and nesting INVOKE calls causes deadlock +due to the way we use mutexes.** + + + FAPI_EXEC_HWP(l_rc , mss::exp::i2c::i2c_get_scom, + myOCMBTarget, static_cast<uint32_t>(l_scomAddr), + io_buffer); + +* The Explorer chip nativly uses 32-bit regs so we must perform two 32-bit operations +(LHS and RHS) in order to get the 64-bits that we expect from the IBM scom + + + fw_reg_read(myOCMBTarget, + translateIbmI2cScomAddr(i_addr, LHS), + l_readBuffer); + + fw_reg_read(myOCMBTarget, + translateIbmI2cScomAddr(i_addr, RHS), + l_readBuffer); + +* The RHS and LHS fw_reg_read calls are nearly identical except the address is 4 bytes more +for the RHS. In both cases the way the fw_reg_read works is to first perform an i2cWrite stating +what address and how many bytes we want to read, then perform an i2c read to get the buffer + + + < build up l_cmd_vector w/ FW_REG_ADDR_LATCH op, op size, addr > + fapi2::putI2c(myOCMBTarget, FW_I2C_SCOM_READ_SIZE, + l_cmd_vector, l_read_data); + + < build up l_cmd_vector w/ FW_REG_READ op > + fapi2::getI2c(myOCMBTarget, FW_I2C_SCOM_READ_SIZE, + l_cmd_vector, l_read_data); + +* The fapi2::getI2c/putI2c calls will drill down into the drive routing similar to how we drilled down to find the i2cScom driver + + + platGetI2c( myOCMBTarget, FW_I2C_SCOM_READ_SIZE + l_cmd_vector, l_read_data) + +* The hostboot platform specific implementation of platGetI2c will lookup the device route for FAPI_I2C ops to OCMB chips + + + deviceRead( myOCMBTarget, l_read_data, + FW_I2C_SCOM_READ_SIZE, DeviceFW::FAPI_I2C, + sizeof(l_cmd_vector), l_cmd_vector); + +* The function associated with FAPI_I2C ops to OCMB chips is fapiI2cPerformOp. This +wrapper function will look up i2c information about the OCMB target and determine +the i2c address for this operation + + + fapiI2cPerformOp(READ , myOCMBTarget, + l_read_data, FW_I2C_SCOM_READ_SIZE, + DeviceFW::FAPI_I2C, sizeof(l_cmd_vector), + l_cmd_vector); + +* Eventually when the i2c info is known we call i2cRead/i2cWrite which will lookup +the device op route for I2C address on the OCMB's master I2c device (which will be a processor). + + + i2cRead( myOCMBTargeti2cMaster, l_read_data, + FW_I2C_SCOM_READ_SIZE, &l_myOCMBTargeti2cInfo, + l_cmd_vector, sizeof(l_cmd_vector)); + +* At this point we will drill down into the platform I2C device driver code + + + deviceOp( DeviceFW::READ, myOCMBTargeti2cMaster, + l_read_data, FW_I2C_SCOM_READ_SIZE, + DEVICE_I2C_ADDRESS_OFFSET(l_myOCMBTargeti2cInfo->port, + l_myOCMBTargeti2cInfo->engine, + l_myOCMBTargeti2cInfo->devAddr, + sizeof(l_cmd_vector), + l_cmd_vector) );
\ No newline at end of file diff --git a/src/usr/expscom/expscomtrace.C b/src/usr/expscom/expscomtrace.C new file mode 100644 index 000000000..1b8fb554c --- /dev/null +++ b/src/usr/expscom/expscomtrace.C @@ -0,0 +1,38 @@ +/* IBM_PROLOG_BEGIN_TAG */ +/* This is an automatically generated prolog. */ +/* */ +/* $Source: src/usr/expscom/expscomtrace.C $ */ +/* */ +/* OpenPOWER HostBoot Project */ +/* */ +/* Contributors Listed Below - COPYRIGHT 2015,2018 */ +/* [+] International Business Machines Corp. */ +/* */ +/* */ +/* Licensed under the Apache License, Version 2.0 (the "License"); */ +/* you may not use this file except in compliance with the License. */ +/* You may obtain a copy of the License at */ +/* */ +/* http://www.apache.org/licenses/LICENSE-2.0 */ +/* */ +/* Unless required by applicable law or agreed to in writing, software */ +/* distributed under the License is distributed on an "AS IS" BASIS, */ +/* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or */ +/* implied. See the License for the specific language governing */ +/* permissions and limitations under the License. */ +/* */ +/* IBM_PROLOG_END_TAG */ +/// +/// @file expscomtrace.C +/// +/// @brief Initialized trace descriptor for expscom +/// + + +#include "expscomtrace.H" +#include <limits.h> +#include <hbotcompid.H> + +// Trace definition +trace_desc_t* g_trac_expscom = nullptr; +TRAC_INIT(&g_trac_expscom, EXPSCOM_COMP_NAME, 2*KILOBYTE);
\ No newline at end of file diff --git a/src/usr/expscom/expscomtrace.H b/src/usr/expscom/expscomtrace.H new file mode 100644 index 000000000..61e1fde78 --- /dev/null +++ b/src/usr/expscom/expscomtrace.H @@ -0,0 +1,39 @@ +/* IBM_PROLOG_BEGIN_TAG */ +/* This is an automatically generated prolog. */ +/* */ +/* $Source: src/usr/expscom/expscomtrace.H $ */ +/* */ +/* OpenPOWER HostBoot Project */ +/* */ +/* Contributors Listed Below - COPYRIGHT 2015,2018 */ +/* [+] International Business Machines Corp. */ +/* */ +/* */ +/* Licensed under the Apache License, Version 2.0 (the "License"); */ +/* you may not use this file except in compliance with the License. */ +/* You may obtain a copy of the License at */ +/* */ +/* http://www.apache.org/licenses/LICENSE-2.0 */ +/* */ +/* Unless required by applicable law or agreed to in writing, software */ +/* distributed under the License is distributed on an "AS IS" BASIS, */ +/* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or */ +/* implied. See the License for the specific language governing */ +/* permissions and limitations under the License. */ +/* */ +/* IBM_PROLOG_END_TAG */ +/// +/// @file expscomtrace.H +/// @brief Defines the extern expscom trace +/// + +#ifndef expscom_TRACE_H_ +#define expscom_TRACE_H_ + +#include <trace/interface.H> +//****************************************************************************** +// Trace descriptors that are defined in matching C file +//****************************************************************************** +extern trace_desc_t* g_trac_expscom; + +#endif // expscom_TRACE_H_
\ No newline at end of file diff --git a/src/usr/expscom/i2cscomdd.C b/src/usr/expscom/i2cscomdd.C new file mode 100644 index 000000000..1cbff6083 --- /dev/null +++ b/src/usr/expscom/i2cscomdd.C @@ -0,0 +1,369 @@ +/* IBM_PROLOG_BEGIN_TAG */ +/* This is an automatically generated prolog. */ +/* */ +/* $Source: src/usr/expscom/i2cscomdd.C $ */ +/* */ +/* OpenPOWER HostBoot Project */ +/* */ +/* Contributors Listed Below - COPYRIGHT 2011,2018 */ +/* [+] International Business Machines Corp. */ +/* */ +/* */ +/* Licensed under the Apache License, Version 2.0 (the "License"); */ +/* you may not use this file except in compliance with the License. */ +/* You may obtain a copy of the License at */ +/* */ +/* http://www.apache.org/licenses/LICENSE-2.0 */ +/* */ +/* Unless required by applicable law or agreed to in writing, software */ +/* distributed under the License is distributed on an "AS IS" BASIS, */ +/* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or */ +/* implied. See the License for the specific language governing */ +/* permissions and limitations under the License. */ +/* */ +/* IBM_PROLOG_END_TAG */ + +/** + * @file i2cscomdd.C + * + * @brief Implementation of I2C SCOM operations to OCMB chip */ + +/*****************************************************************************/ +// I n c l u d e s +/*****************************************************************************/ +#include <errl/errlmanager.H> // errlCommit +#include <lib/i2c/exp_i2c_scom.H> // i2c_get_scom +#include <errl/errludtarget.H> // ErrlUserDetailsTarget +#include <hwpf/fapi2/include/fapi2_hwp_executor.H> // FAPI_EXEC_HWP +#include <expscom/expscom_reasoncodes.H> // EXPSCOM::MOD_I2CSCOM_PERFORM_OP +#include "i2cscomdd.H" //i2cScomPerformOp +#include "expscomtrace.H" //g_trac_expscom + +namespace I2CSCOMDD +{ + +constexpr uint64_t FIRST_4_BYTES = 0xFFFFFFFF00000000; + +/** + * @brief Performs validation of params passed into i2cScomPerformOp function + * This function checks that the target type, the address format, the buffer length + * and the op type are all valid. A unique error will be created for each violation. + * If multiple error are found the last error will be returned and all previous errors + * found will be committed as new errors are found (see function). + * + * @param[in] i_opType Operation type, see DeviceFW::OperationType + * in driverif.H + * @param[in] i_target TARGETING::Target passed to i2cScomPerformOp + * @param[in] i_buflen size of buffer passed to i2cScomPerformOp + * (i_buflen is expected to be 8 bytes) + * @param[in] i_scomAddr Scom address operation will be performed on + + * @return errlHndl_t nullptr on success, non-null ptr on error + */ +errlHndl_t validateInputs(DeviceFW::OperationType i_opType, + const TARGETING::Target* i_target, + size_t i_buflen, + uint64_t i_scomAddr); + +/////////////////////////////////////////////////////////////////////////////// +// See header for doxygen documentation +/////////////////////////////////////////////////////////////////////////////// +errlHndl_t i2cScomPerformOp(DeviceFW::OperationType i_opType, + TARGETING::Target* i_target, + void* io_buffer, + size_t& io_buflen, + int64_t i_accessType, + va_list i_args) +{ + errlHndl_t l_err = nullptr; + fapi2::ReturnCode l_rc = fapi2::FAPI2_RC_SUCCESS; + // The only extra arg should be the scomAddress + uint64_t l_scomAddr = va_arg(i_args,uint64_t); + + // The fapi2 put/get i2cScom interfaces require a fapi2::buffer so convert + // to a uint64_t buffer (for IBM scom) and uint32_t buffer (for Microchip scoms) + fapi2::buffer<uint64_t> l_fapi2Buffer64(*reinterpret_cast<uint64_t *>(io_buffer)); + fapi2::buffer<uint32_t> l_fapi2Buffer32; + l_fapi2Buffer64.extractToRight<32,32>(l_fapi2Buffer32); + + do + { + // First make sure the inputs are valid + l_err = validateInputs ( i_opType, i_target, l_scomAddr, io_buflen); + + if(l_err) + { + break; + } + + // Check if this is a IBM_SCOM address by &ing the address with IBM_SCOM_INDICATOR + // If the indicator is not set, then we will assume this is a microChip address + if( (l_scomAddr & mss::exp::i2c::IBM_SCOM_INDICATOR) == mss::exp::i2c::IBM_SCOM_INDICATOR) + { + // READ and WRITE equates to i2c_get_scom and i2c_put_scom respectively. any other OP is invalid + // i/o data is expected to be 8 bytes for IBM scoms + if(i_opType == DeviceFW::READ) + { + FAPI_EXEC_HWP(l_rc , mss::exp::i2c::i2c_get_scom, + i_target, static_cast<uint32_t>(l_scomAddr), + l_fapi2Buffer64); + + l_err = fapi2::rcToErrl(l_rc); + if(l_err) + { + // Sizes stolen from plat_hwp_invoker.H + l_err->collectTrace(FAPI_IMP_TRACE_NAME, 256); + l_err->collectTrace(FAPI_TRACE_NAME, 384); + TRACFCOMP( g_trac_expscom, ERR_MRK "i2cScomPerformOp> i2c_get_scom failed for HUID 0x%x Address 0x%lx ", + TARGETING::get_huid(i_target), l_scomAddr ); + } + else + { + // Copy contents of what we read to io_buffer + memcpy(io_buffer, reinterpret_cast<uint8_t *>(l_fapi2Buffer64.pointer()), sizeof(uint64_t)); + } + } + else + { + FAPI_EXEC_HWP(l_rc , mss::exp::i2c::i2c_put_scom, i_target, static_cast<uint32_t>(l_scomAddr), l_fapi2Buffer64); + l_err = fapi2::rcToErrl(l_rc); + if(l_err) + { + // Sizes stolen from plat_hwp_invoker.H + l_err->collectTrace(FAPI_IMP_TRACE_NAME, 256); + l_err->collectTrace(FAPI_TRACE_NAME, 384); + TRACFCOMP( g_trac_expscom, ERR_MRK "i2cScomPerformOp> i2c_put_scom failed for HUID 0x%x Address 0x%lx ", + TARGETING::get_huid(i_target), l_scomAddr ); + } + } + } + else + { + // READ and WRITE equates to i2c_get_scom and i2c_put_scom respectively. any other OP is invalid + // i/o data is expected to be 4 bytes for Microchip scoms + if(i_opType == DeviceFW::READ) + { + FAPI_EXEC_HWP(l_rc , mss::exp::i2c::i2c_get_scom, i_target, static_cast<uint32_t>(l_scomAddr), l_fapi2Buffer32); + l_err = fapi2::rcToErrl(l_rc); + if(l_err) + { + // Sizes stolen from plat_hwp_invoker.H + l_err->collectTrace(FAPI_IMP_TRACE_NAME, 256); + l_err->collectTrace(FAPI_TRACE_NAME, 384); + TRACFCOMP( g_trac_expscom, ERR_MRK "i2cScomPerformOp> i2c_get_scom failed for HUID 0x%x Address 0x%lx ", + TARGETING::get_huid(i_target), l_scomAddr ); + } + else + { + // Put the contexts of the 32 bit buffer right justified into the 64 bit buffer + l_fapi2Buffer64.flush<0>(); + l_fapi2Buffer64.insertFromRight<32,32>(l_fapi2Buffer32); + // Copy contents of 64 bit buffer to io_buffer + memcpy(io_buffer, reinterpret_cast<uint8_t *>(l_fapi2Buffer64.pointer()), sizeof(uint64_t)); + } + } + else + { + FAPI_EXEC_HWP(l_rc , mss::exp::i2c::i2c_put_scom, i_target, static_cast<uint32_t>(l_scomAddr), l_fapi2Buffer32); + l_err = fapi2::rcToErrl(l_rc); + if(l_err) + { + // Sizes stolen from plat_hwp_invoker.H + l_err->collectTrace(FAPI_IMP_TRACE_NAME, 256); + l_err->collectTrace(FAPI_TRACE_NAME, 384); + TRACFCOMP( g_trac_expscom, ERR_MRK "i2cScomPerformOp> i2c_put_scom failed for HUID 0x%x Address 0x%lx ", + TARGETING::get_huid(i_target), l_scomAddr ); + } + } + + } + + } while (0); + return l_err; +} + +/////////////////////////////////////////////////////////////////////////////// +// See above for doxygen documentation +/////////////////////////////////////////////////////////////////////////////// +errlHndl_t validateInputs(DeviceFW::OperationType i_opType, + const TARGETING::Target* i_target, + size_t i_buflen, + uint64_t i_scomAddr) +{ + errlHndl_t l_err = nullptr; + uint32_t l_commonPlid = 0; // If there are multiple issues found link logs with first + + TARGETING::ATTR_MODEL_type l_targetModel = + i_target->getAttr<TARGETING::ATTR_MODEL>(); + + // Only target we can perform i2c scoms on like this are explorer OCMB chip targets + if( l_targetModel != TARGETING::MODEL_EXPLORER ) + { + TRACFCOMP( g_trac_expscom, ERR_MRK "i2cScomPerformOp> Invalid model type : l_targetModel=%d", l_targetModel ); + /*@ + * @errortype + * @moduleid EXPSCOM::MOD_I2CSCOM_PERFORM_OP + * @reasoncode EXPSCOM::RC_INVALID_MODEL_TYPE + * @userdata1 SCOM Address + * @userdata2[0:31] Model Type + * @userdata2[32:63] Target Huid + * @devdesc i2cScomPerformOp> Invalid target type (!= OCMB_CHP) + * @custdesc A problem occurred during the IPL of the system: + * Invalid target type for a SCOM operation. + */ + l_err = new ERRORLOG::ErrlEntry(ERRORLOG::ERRL_SEV_UNRECOVERABLE, + EXPSCOM::MOD_I2CSCOM_PERFORM_OP, + EXPSCOM::RC_INVALID_MODEL_TYPE, + i_scomAddr, + TWO_UINT32_TO_UINT64(l_targetModel, + TARGETING::get_huid(i_target)), + ERRORLOG::ErrlEntry::ADD_SW_CALLOUT); + + l_err->collectTrace(EXPSCOM_COMP_NAME); + ERRORLOG::ErrlUserDetailsTarget(i_target,"SCOM Target"). + addToLog(l_err); + l_commonPlid = l_err->plid(); + } + // The address is really only 32 bits, we will cast it to 32 bits before passing to + // the fapi2 i2c_get_scom function but just to be safe make sure that first 4 bytes are 0s + if( i_scomAddr & FIRST_4_BYTES ) + { + TRACFCOMP( g_trac_expscom, + ERR_MRK "i2cScomPerformOp> Invalid address : i_scomAddr=0x%lx , first 32 bits should be 0's", + i_scomAddr ); + + // If there is already an error from prev checks, then commit it + if(l_err) + { + errlCommit(l_err, EXPSCOM_COMP_ID); + } + + /*@ + * @errortype + * @moduleid EXPSCOM::MOD_I2CSCOM_PERFORM_OP + * @reasoncode EXPSCOM::RC_INVALID_ADDRESS + * @userdata1 SCOM Address + * @userdata2 Target HUID + * @devdesc i2cScomPerformOp> Invalid scom address, first 4 + * bytes should be 0's + * @custdesc A problem occurred during the IPL of the system: + * Invalid address for a SCOM operation. + */ + l_err = new ERRORLOG::ErrlEntry(ERRORLOG::ERRL_SEV_UNRECOVERABLE, + EXPSCOM::MOD_I2CSCOM_PERFORM_OP, + EXPSCOM::RC_INVALID_ADDRESS, + i_scomAddr, + TARGETING::get_huid(i_target), + ERRORLOG::ErrlEntry::ADD_SW_CALLOUT); + + l_err->collectTrace(EXPSCOM_COMP_NAME); + ERRORLOG::ErrlUserDetailsTarget(i_target,"SCOM Target"). + addToLog(l_err); + + if(l_commonPlid == 0) + { + l_commonPlid = l_err->plid(); + } + else + { + l_err->plid(l_commonPlid); + } + } + + // The buffer passed into i2cScomPerformOp should ALWAYS be 8 bytes. + // If it is an IBM scom then all 8 bytes are used. If its microchip scom + // then only the last 4 bytes are used. + if (i_buflen != sizeof(uint64_t)) + { + TRACFCOMP( g_trac_expscom, ERR_MRK "i2cScomPerformOp> Invalid data length : io_buflen=%d ," + " expected sizeof(uint64_t)", i_buflen ); + + // If there is already an error from prev checks, then commit it + if(l_err) + { + errlCommit(l_err, EXPSCOM_COMP_ID); + } + + /*@ + * @errortype + * @moduleid EXPSCOM::MOD_I2CSCOM_PERFORM_OP + * @reasoncode EXPSCOM::RC_INVALID_LENGTH + * @userdata1 SCOM Address + * @userdata2 Data Length + * @devdesc i2cScomPerformOp> Invalid data length (!= 8 bytes) + * @custdesc A problem occurred during the IPL of the system: + * Invalid data length for a SCOM operation. + */ + l_err = new ERRORLOG::ErrlEntry(ERRORLOG::ERRL_SEV_UNRECOVERABLE, + EXPSCOM::MOD_I2CSCOM_PERFORM_OP, + EXPSCOM::RC_INVALID_LENGTH, + i_scomAddr, + TO_UINT64(i_buflen), + ERRORLOG::ErrlEntry::ADD_SW_CALLOUT); + + l_err->collectTrace(EXPSCOM_COMP_NAME); + ERRORLOG::ErrlUserDetailsTarget(i_target,"SCOM Target"). + addToLog(l_err); + + if(l_commonPlid == 0) + { + l_commonPlid = l_err->plid(); + } + else + { + l_err->plid(l_commonPlid); + } + } + + // The only valid operations are READ and WRITE if anything else comes in we need to error out + if (i_opType != DeviceFW::READ && i_opType != DeviceFW::WRITE ) + { + TRACFCOMP( g_trac_expscom, ERR_MRK "i2cScomPerformOp> Invalid operation type : i_opType=%d", i_opType ); + + if(l_err) + { + errlCommit(l_err, EXPSCOM_COMP_ID); + } + + /*@ + * @errortype + * @moduleid EXPSCOM::MOD_I2CSCOM_PERFORM_OP + * @reasoncode EXPSCOM::RC_INVALID_OPTYPE + * @userdata1 SCOM Address + * @userdata2 Op Type + * @devdesc i2cScomPerformOp> Invalid operation type (!= READ or WRITE) + * @custdesc A problem occurred during the IPL of the system: + * Invalid SCOM operation. + */ + l_err = new ERRORLOG::ErrlEntry(ERRORLOG::ERRL_SEV_UNRECOVERABLE, + EXPSCOM::MOD_I2CSCOM_PERFORM_OP, + EXPSCOM::RC_INVALID_OPTYPE, + i_scomAddr, + i_opType, + ERRORLOG::ErrlEntry::ADD_SW_CALLOUT); + + l_err->collectTrace(EXPSCOM_COMP_NAME); + ERRORLOG::ErrlUserDetailsTarget(i_target,"SCOM Target"). + addToLog(l_err); + + if(l_commonPlid == 0) + { + l_commonPlid = l_err->plid(); + } + else + { + l_err->plid(l_commonPlid); + } + } + + return l_err; +} + + +DEVICE_REGISTER_ROUTE(DeviceFW::WILDCARD, + DeviceFW::I2CSCOM, + TARGETING::TYPE_OCMB_CHIP, + i2cScomPerformOp); + + +}
\ No newline at end of file diff --git a/src/usr/expscom/i2cscomdd.H b/src/usr/expscom/i2cscomdd.H new file mode 100644 index 000000000..07c025037 --- /dev/null +++ b/src/usr/expscom/i2cscomdd.H @@ -0,0 +1,67 @@ +/* IBM_PROLOG_BEGIN_TAG */ +/* This is an automatically generated prolog. */ +/* */ +/* $Source: src/usr/expscom/i2cscomdd.H $ */ +/* */ +/* OpenPOWER HostBoot Project */ +/* */ +/* Contributors Listed Below - COPYRIGHT 2011,2018 */ +/* [+] International Business Machines Corp. */ +/* */ +/* */ +/* Licensed under the Apache License, Version 2.0 (the "License"); */ +/* you may not use this file except in compliance with the License. */ +/* You may obtain a copy of the License at */ +/* */ +/* http://www.apache.org/licenses/LICENSE-2.0 */ +/* */ +/* Unless required by applicable law or agreed to in writing, software */ +/* distributed under the License is distributed on an "AS IS" BASIS, */ +/* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or */ +/* implied. See the License for the specific language governing */ +/* permissions and limitations under the License. */ +/* */ +/* IBM_PROLOG_END_TAG */ +#ifndef __I2CSCOMDD_H +#define __I2CSCOMDD_H + +/** @file i2cscomdd.H + * @brief Provides the interfaces to perform I2cscom + */ +#include <stdint.h> + + +namespace I2CSCOMDD +{ + +/** + * @brief Performs an I2CSCOM access operation + * This function performs an I2CSCOM access operation. It follows a pre-defined + * prototype functions in order to be registered with the device-driver + * framework. + * + * @param[in] i_opType Operation type, see DeviceFW::OperationType + * in driverif.H + * @param[in] i_target I2CSCOM Explorer Chip target + * @param[in/out] io_buffer Read: Pointer to output data storage + * Write: Pointer to input data storage + * @param[in/out] io_buflen Input: size of io_buffer (in bytes) + * Output: + * Read: Size of output data + * Write: Size of data written + * @param[in] i_accessType DeviceFW::AccessType enum (usrif.H) + * @param[in] i_args This is an argument list for DD framework. + * In this function, there's only one argument, + * which is the IBM scom address + * @return errlHndl_t nullptr on success, non-null ptr on error + */ +errlHndl_t i2cscomPerformOp(DeviceFW::OperationType i_opType, + TARGETING::Target* i_target, + void* io_buffer, + size_t& io_buflen, + int64_t i_accessType, + va_list i_args); + +} + +#endif // __I2CSCOMDD_H
\ No newline at end of file diff --git a/src/usr/expscom/makefile b/src/usr/expscom/makefile new file mode 100644 index 000000000..f8569d329 --- /dev/null +++ b/src/usr/expscom/makefile @@ -0,0 +1,42 @@ +# IBM_PROLOG_BEGIN_TAG +# This is an automatically generated prolog. +# +# $Source: src/usr/expscom/makefile $ +# +# OpenPOWER HostBoot Project +# +# Contributors Listed Below - COPYRIGHT 2011,2018 +# [+] International Business Machines Corp. +# +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or +# implied. See the License for the specific language governing +# permissions and limitations under the License. +# +# IBM_PROLOG_END_TAG +ROOTPATH = ../../.. +MODULE = expscom + +EXTRAINCDIR += ${ROOTPATH}/src/import +EXTRAINCDIR += ${ROOTPATH}/src/import/chips/ocmb/explorer/procedures/hwp/memory/ +EXTRAINCDIR += ${ROOTPATH}/src/import/chips/common/utils/imageProcs +EXTRAINCDIR += ${ROOTPATH}/src/import/chips/p9/procedures/hwp/ffdc/ +EXTRAINCDIR += ${ROOTPATH}/src/import/hwpf/fapi2/include +EXTRAINCDIR += ${ROOTPATH}/src/include/usr/fapi2 + + +OBJS += expscomtrace.o +OBJS += i2cscomdd.o +# OBJS += mmioscom.o +# TODO RTC:196806 ADD TESTs +#SUBDIRS += test.d + +include ${ROOTPATH}/config.mk
\ No newline at end of file diff --git a/src/usr/fapi2/fapi2.mk b/src/usr/fapi2/fapi2.mk index 9e2032470..0d631c8ff 100755 --- a/src/usr/fapi2/fapi2.mk +++ b/src/usr/fapi2/fapi2.mk @@ -123,6 +123,8 @@ FAPI2_ERROR_XML += $(wildcard \ $(ROOTPATH)/src/import/chips/centaur/procedures/xml/error_info/*.xml) FAPI2_ERROR_XML += $(wildcard \ $(ROOTPATH)/src/import/generic/procedures/xml/error_info/*.xml) +FAPI2_ERROR_XML += $(wildcard \ + $(ROOTPATH)/src/import/chips/ocmb/explorer/procedures/xml/error_info/*.xml) # Attribute XML files. FAPI2_ATTR_XML += $(wildcard \ @@ -133,6 +135,8 @@ FAPI2_ATTR_XML += $(wildcard \ $(ROOTPATH)/src/import/chips/centaur/procedures/xml/attribute_info/*.xml) FAPI2_ATTR_XML += $(wildcard \ $(ROOTPATH)/src/import/generic/procedures/xml/attribute_info/*.xml) +FAPI2_ATTR_XML += $(wildcard \ + $(ROOTPATH)/src/import/chips/ocmb/explorer/procedures/xml/attribute_info/*.xml) # Filter out Temp defaults XML file from Attribute XML files. # NOTE: The hb_temp_defaults.xml file is not a normal attribute file with the diff --git a/src/usr/initservice/extinitsvc/extinitsvctasks.H b/src/usr/initservice/extinitsvc/extinitsvctasks.H index b6961b622..f7ddb7f2d 100644 --- a/src/usr/initservice/extinitsvc/extinitsvctasks.H +++ b/src/usr/initservice/extinitsvc/extinitsvctasks.H @@ -380,6 +380,18 @@ const TaskInfo g_exttaskinfolist[] = { }, /** + * @brief Explorer Scom library + */ + { + "libexpscom.so" , // taskname + NULL, // no pointer to fn + { + INIT_TASK, // task type + EXT_IMAGE, // Extended Module + } + }, + + /** * @brief Common istep functions * * diff --git a/src/usr/makefile b/src/usr/makefile index a5961b89d..c2c0f5b35 100644 --- a/src/usr/makefile +++ b/src/usr/makefile @@ -29,49 +29,50 @@ ROOTPATH = ../.. HOSTBOOT_PROFILE_NO_INSTRUMENT = 1 OBJS += module_init.o -SUBDIRS += sio.d -SUBDIRS += isteps.d -SUBDIRS += trace.d +SUBDIRS += console.d SUBDIRS += cxxtest.d -SUBDIRS += testcore.d -SUBDIRS += errl.d SUBDIRS += devicefw.d -SUBDIRS += scom.d -SUBDIRS += xscom.d -SUBDIRS += targeting.d -SUBDIRS += initservice.d +SUBDIRS += diag.d +SUBDIRS += dump.d +SUBDIRS += errl.d +SUBDIRS += errldisplay.d +SUBDIRS += expscom.d SUBDIRS += fapi2.d -SUBDIRS += pnor.d -SUBDIRS += i2c.d -SUBDIRS += vfs.d SUBDIRS += fsi.d -SUBDIRS += hwas.d SUBDIRS += fsiscom.d -SUBDIRS += intr.d -SUBDIRS += util.d -SUBDIRS += mbox.d -SUBDIRS += vpd.d -SUBDIRS += scan.d -SUBDIRS += runtime.d +SUBDIRS += gpio.d +SUBDIRS += $(if $(CONFIG_ENABLE_HDAT_IN_HOSTBOOT),hdat.d,) +SUBDIRS += $(if $(CONFIG_HTMGT),htmgt.d) +SUBDIRS += hwas.d +SUBDIRS += hwplibs.d +SUBDIRS += i2c.d SUBDIRS += ibscom.d -SUBDIRS += dump.d -SUBDIRS += secureboot.d -SUBDIRS += sbe.d SUBDIRS += imageprocs.d -SUBDIRS += sbeio.d -SUBDIRS += gpio.d -SUBDIRS += lpc.d -SUBDIRS += console.d -SUBDIRS += errldisplay.d SUBDIRS += $(if $(CONFIG_BMC_BT_LPC_IPMI),ipmibase.d) SUBDIRS += $(if $(CONFIG_BMC_BT_LPC_IPMI),ipmiext.d) -SUBDIRS += $(if $(CONFIG_HTMGT),htmgt.d) -SUBDIRS += diag.d -SUBDIRS += xz.d -SUBDIRS += hwplibs.d +SUBDIRS += initservice.d +SUBDIRS += intr.d +SUBDIRS += isteps.d +SUBDIRS += lpc.d +SUBDIRS += mbox.d SUBDIRS += mmio.d -SUBDIRS += $(if $(CONFIG_ENABLE_HDAT_IN_HOSTBOOT),hdat.d,) SUBDIRS += $(if $(CONFIG_FSP_BUILD),,nvram.d) +SUBDIRS += pnor.d +SUBDIRS += runtime.d +SUBDIRS += sbe.d +SUBDIRS += sbeio.d +SUBDIRS += scan.d +SUBDIRS += scom.d +SUBDIRS += secureboot.d +SUBDIRS += sio.d +SUBDIRS += targeting.d +SUBDIRS += testcore.d +SUBDIRS += trace.d +SUBDIRS += util.d +SUBDIRS += vfs.d +SUBDIRS += vpd.d +SUBDIRS += xscom.d +SUBDIRS += xz.d #errldisplay relies on some generated files from PRD. #Enforce that it goes after diff --git a/src/usr/scom/scom.C b/src/usr/scom/scom.C index 1a4ba857f..22567fb49 100644 --- a/src/usr/scom/scom.C +++ b/src/usr/scom/scom.C @@ -133,6 +133,10 @@ DEVICE_REGISTER_ROUTE(DeviceFW::WILDCARD, TARGETING::TYPE_MEMBUF, scomMemBufPerformOp); +DEVICE_REGISTER_ROUTE(DeviceFW::WILDCARD, + DeviceFW::SCOM, + TARGETING::TYPE_OCMB_CHIP, + scomPerformOp); /////////////////////////////////////////////////////////////////////////////// /////////////////////////////////////////////////////////////////////////////// @@ -879,14 +883,18 @@ errlHndl_t doScomOp(DeviceFW::OperationType i_opType, do{ TARGETING::ScomSwitches scomSetting; + // We start by assuming target = MASTER_PROCESSOR_CHIP_TARGET_SENTINEL + // so following that assumption default l_targetType to PROC_CHIP + TARGETING::ATTR_TYPE_type l_targetType = TARGETING::TYPE_PROC; scomSetting.useXscom = true; //Default to Xscom supported. if(TARGETING::MASTER_PROCESSOR_CHIP_TARGET_SENTINEL != i_target) { scomSetting = i_target->getAttr<TARGETING::ATTR_SCOM_SWITCHES>(); - if( TARGETING::TYPE_PROC - == i_target->getAttr<TARGETING::ATTR_TYPE>() ) + l_targetType = i_target->getAttr<TARGETING::ATTR_TYPE>(); + + if( l_targetType == TARGETING::TYPE_PROC ) { l_multicastBugError = true; } @@ -926,6 +934,17 @@ errlHndl_t doScomOp(DeviceFW::OperationType i_opType, } break; } + else if(scomSetting.useI2cScom) + { + //do I2CSCOM + l_err = deviceOp(i_opType, + i_target, + io_buffer, + io_buflen, + DEVICE_I2CSCOM_ADDRESS(i_addr)); + if( l_err ) { break; } + + } else if(scomSetting.useSbeScom) { //do SBESCOM l_err = deviceOp(i_opType, diff --git a/src/usr/targeting/common/Targets.pm b/src/usr/targeting/common/Targets.pm index 48cc85a70..b5597a711 100644 --- a/src/usr/targeting/common/Targets.pm +++ b/src/usr/targeting/common/Targets.pm @@ -1509,6 +1509,7 @@ sub processMc # It's okay to hard code these here because the code fixes it as needed # This is hardcoded for proc target as well. $self->setAttributeField($membuf, "SCOM_SWITCHES", "useSbeScom","0"); + $self->setAttributeField($membuf, "SCOM_SWITCHES", "useI2cScom","0"); $self->setAttributeField($membuf, "SCOM_SWITCHES", "useFsiScom","1"); $self->setAttributeField($membuf, "SCOM_SWITCHES", "reserved", "0"); $self->setAttributeField($membuf, "SCOM_SWITCHES", "useInbandScom", "0"); diff --git a/src/usr/targeting/common/processMrw.pl b/src/usr/targeting/common/processMrw.pl index ead7ee620..cf19ec266 100755 --- a/src/usr/targeting/common/processMrw.pl +++ b/src/usr/targeting/common/processMrw.pl @@ -1085,6 +1085,7 @@ sub processProcessor $targetObj->setAttributeField($target, "SCOM_SWITCHES", "useInbandScom", "0"); $targetObj->setAttributeField($target, "SCOM_SWITCHES", "useXscom", "0"); + $targetObj->setAttributeField($target, "SCOM_SWITCHES", "useI2cScom","0"); ## default effective fabric ids to match regular fabric ids ## the value will be adjusted based on presence detection later diff --git a/src/usr/targeting/common/xmltohb/attribute_types.xml b/src/usr/targeting/common/xmltohb/attribute_types.xml index 0b1b9bf9b..e7f97fc6f 100644 --- a/src/usr/targeting/common/xmltohb/attribute_types.xml +++ b/src/usr/targeting/common/xmltohb/attribute_types.xml @@ -6741,7 +6741,17 @@ <type>uint8_t</type> </field> <field> - <bits>4</bits> + <bits>1</bits> + <default>0</default> + <description> + 0b0: Do not use I2C SCOM at this time. + 0b1: Use I2C SCOM at this time + </description> + <name>useI2cScom</name> + <type>uint8_t</type> + </field> + <field> + <bits>3</bits> <default>0</default> <description>Reserved for future expansion</description> <name>reserved</name> diff --git a/src/usr/targeting/common/xmltohb/target_types.xml b/src/usr/targeting/common/xmltohb/target_types.xml index 903d749e3..8557964d8 100644 --- a/src/usr/targeting/common/xmltohb/target_types.xml +++ b/src/usr/targeting/common/xmltohb/target_types.xml @@ -319,6 +319,10 @@ <value>0</value> </field> <field> + <id>useI2cScom</id> + <value>0</value> + </field> + <field> <id>useInbandScom</id> <value>0</value> </field> @@ -386,6 +390,35 @@ <default>EXPLORER</default> <id>MODEL</id> </attribute> + <attribute> + <default> + <field> + <id>reserved</id> + <value>0</value> + </field> + <field> + <id>useFsiScom</id> + <value>0</value> + </field> + <field> + <id>useI2cScom</id> + <value>1</value> + </field> + <field> + <id>useInbandScom</id> + <value>0</value> + </field> + <field> + <id>useSbeScom</id> + <value>0</value> + </field> + <field> + <id>useXscom</id> + <value>0</value> + </field> + </default> + <id>SCOM_SWITCHES</id> + </attribute> </targetType> <targetType> |