summaryrefslogtreecommitdiffstats
path: root/src/usr/xscom
diff options
context:
space:
mode:
authorDan Crowell <dcrowell@us.ibm.com>2017-02-13 22:46:45 -0600
committerDaniel M. Crowell <dcrowell@us.ibm.com>2017-02-16 14:31:39 -0500
commit6f93bd233e0f1ffddc7b97cb4be83a944d4483d1 (patch)
treec68765612bca6478b0e18b4b3d172d3d44232bc6 /src/usr/xscom
parent1987418a47791b77d59c5f231078bfb39ca2b045 (diff)
downloadtalos-hostboot-6f93bd233e0f1ffddc7b97cb4be83a944d4483d1.tar.gz
talos-hostboot-6f93bd233e0f1ffddc7b97cb4be83a944d4483d1.zip
XSCOM/LPC Workaround for Nimbus DD1
There is a shared resource between the XSCOM and LPC logic that leads to errors at the XSCOM level causing errors to be detected during LPC operations. This commit adds an external interface to access block LPC operations while an XSCOM operation is in flight. Change-Id: I571094dfb666aa9198fabec5280a0f45c62c90ba RTC: 167291 Reviewed-on: http://ralgit01.raleigh.ibm.com/gerrit1/36399 Tested-by: Jenkins Server <pfd-jenkins+hostboot@us.ibm.com> Tested-by: Jenkins OP Build CI <op-jenkins+hostboot@us.ibm.com> Tested-by: FSP CI Jenkins <fsp-CI-jenkins+hostboot@us.ibm.com> Reviewed-by: Thi N. Tran <thi@us.ibm.com> Reviewed-by: Dean Sanner <dsanner@us.ibm.com> Reviewed-by: Daniel M. Crowell <dcrowell@us.ibm.com>
Diffstat (limited to 'src/usr/xscom')
-rw-r--r--src/usr/xscom/xscom.C48
1 files changed, 47 insertions, 1 deletions
diff --git a/src/usr/xscom/xscom.C b/src/usr/xscom/xscom.C
index fb487c55b..b112b2294 100644
--- a/src/usr/xscom/xscom.C
+++ b/src/usr/xscom/xscom.C
@@ -5,7 +5,7 @@
/* */
/* OpenPOWER HostBoot Project */
/* */
-/* Contributors Listed Below - COPYRIGHT 2011,2016 */
+/* Contributors Listed Below - COPYRIGHT 2011,2017 */
/* [+] International Business Machines Corp. */
/* */
/* */
@@ -47,6 +47,7 @@
#include <errl/errludlogregister.H>
#include <xscom/piberror.H>
#include <arch/pirformat.H>
+#include <lpc/lpcif.H>
// Trace definition
trace_desc_t* g_trac_xscom = NULL;
@@ -701,6 +702,38 @@ void collectXscomFFDC(TARGETING::Target* i_target,
///////////////////////////////////////////////////////////////////////////////
///////////////////////////////////////////////////////////////////////////////
+bool checkForLpcBug( void )
+{
+ // See HW400314 for description of hardware bug
+ // The Power Bus Snooper Interface on the ADU is shared by both PIB
+ // and LPC. Once an error occurred in the Xscom while accessing the
+ // PIB space, the interface is overriding the data that is sent out
+ // as all ?F? for any operation which may be XSCOM to PIB address
+ // space or to a LPC address Space. Further XSCOM operation are
+ // locked till the pending error is cleared. But an XSCOM Status
+ // pmisc is sent with pib response info (in this case the type of
+ // the error) and for the next operations i.e. XSCOM to PIB or to
+ // LPC it sends info value as 1 which indicates ADU has pending
+ // XSCOM Error. This is indicated in the (48 :50) bits in the address
+ // sent.
+
+ ProcessorCoreType l_coreType = cpu_core_type();
+ uint8_t l_ddLevel = cpu_dd_level();
+
+ // Bug is only present in Nimbus DD1
+ if( (l_coreType == CORE_POWER9_NIMBUS) && (l_ddLevel == 0x10) )
+ {
+ TRACFCOMP( g_trac_xscom, "Activating LPC mutex workaround" );
+ return true;
+ }
+ else
+ {
+ return false;
+ }
+}
+
+///////////////////////////////////////////////////////////////////////////////
+///////////////////////////////////////////////////////////////////////////////
errlHndl_t xscomPerformOp(DeviceFW::OperationType i_opType,
TARGETING::Target* i_target,
void* io_buffer,
@@ -738,6 +771,13 @@ errlHndl_t xscomPerformOp(DeviceFW::OperationType i_opType,
// Pin this thread to current CPU
task_affinity_pin();
+ // Block the LPC driver from running while an xscom is in progress
+ static bool l_hasLpcBug = checkForLpcBug();
+ if( l_hasLpcBug )
+ {
+ LPC::block_lpc_ops(true);
+ }
+
// Lock other XSCom in this same thread from running
l_XSComMutex = mmio_xscom_mutex();
mutex_lock(l_XSComMutex);
@@ -778,6 +818,12 @@ errlHndl_t xscomPerformOp(DeviceFW::OperationType i_opType,
// Unlock
mutex_unlock(l_XSComMutex);
+ // Unblock the LPC driver
+ if( l_hasLpcBug )
+ {
+ LPC::block_lpc_ops(false);
+ }
+
// Done, un-pin
task_affinity_unpin();
OpenPOWER on IntegriCloud