summaryrefslogtreecommitdiffstats
path: root/src/occ_405/amec/amec_sensors_fw.c
diff options
context:
space:
mode:
authormbroyles <mbroyles@us.ibm.com>2017-07-26 14:36:03 -0500
committerWilliam A. Bryan <wilbryan@us.ibm.com>2017-07-26 16:47:13 -0400
commit458a99921f4ed89d145d267ba837eb3228909d06 (patch)
tree2f315b5db7466443274061a847a145a080fc2809 /src/occ_405/amec/amec_sensors_fw.c
parent579fd543e9d698dc3932e8f72b166233f8baa773 (diff)
downloadtalos-occ-458a99921f4ed89d145d267ba837eb3228909d06.tar.gz
talos-occ-458a99921f4ed89d145d267ba837eb3228909d06.zip
Reduce number of checks when waiting for SPI completion
Fix GPE1 timing fw sensor Change-Id: I4e0d4256b0f55a5593b16237ace5bce73029f6da CQ: SW396887 Reviewed-on: http://ralgit01.raleigh.ibm.com/gerrit1/43706 Tested-by: FSP CI Jenkins <fsp-CI-jenkins+hostboot@us.ibm.com> Reviewed-by: Christopher J. Cain <cjcain@us.ibm.com> Reviewed-by: Andres A. Lugo-Reyes <aalugore@us.ibm.com> Reviewed-by: William A. Bryan <wilbryan@us.ibm.com>
Diffstat (limited to 'src/occ_405/amec/amec_sensors_fw.c')
-rw-r--r--src/occ_405/amec/amec_sensors_fw.c261
1 files changed, 141 insertions, 120 deletions
diff --git a/src/occ_405/amec/amec_sensors_fw.c b/src/occ_405/amec/amec_sensors_fw.c
index 525890a..fb3b9fe 100644
--- a/src/occ_405/amec/amec_sensors_fw.c
+++ b/src/occ_405/amec/amec_sensors_fw.c
@@ -79,182 +79,203 @@ void amec_slv_update_smh_sensors(int i_smh_state, uint32_t i_duration)
void amec_slv_update_gpe_sensors(uint8_t i_gpe_engine)
{
// Update the duration in the fw timing table
- G_fw_timing.gpe_dur[i_gpe_engine] = DURATION_IN_US_UNTIL_NOW_FROM(G_fw_timing.rtl_start_gpe);
+ G_fw_timing.gpe_dur[i_gpe_engine] = DURATION_IN_US_UNTIL_NOW_FROM(G_fw_timing.rtl_start_gpe[i_gpe_engine]);
}
-
// Function Specification
//
-// Name: amec_update_fw_sensors
+// Name: task_gpe_timings
//
-// Description: Updates sensors related to the OCC FW Timings
+// Description: Kick off tasks to time GPEs
//
// Thread: RealTime Loop
//
// End Function Specification
#define MAX_CONSEC_TRACE 4
-void amec_update_fw_sensors(void)
+void task_gpe_timings(task_t * i_task)
{
errlHndl_t l_err = NULL;
int rc = 0;
int rc2 = 0;
- static bool l_first_call = TRUE;
+ static bool L_first_call = TRUE;
bool l_gpe0_idle, l_gpe1_idle;
static uint8_t L_consec_trace_count[2] = {0};
-
- // ------------------------------------------------------
- // Update OCC Firmware Sensors from last tick
- // ------------------------------------------------------
- int l_last_state = G_fw_timing.amess_state;
- // RTLtickdur = duration of last tick's RTL ISR (max = 250us)
- sensor_update( AMECSENSOR_PTR(RTLtickdur), G_fw_timing.rtl_dur);
- // AMEintdur = duration of last tick's AMEC portion of RTL ISR
- sensor_update( AMECSENSOR_PTR(AMEintdur), G_fw_timing.ameint_dur);
- // AMESSdurX = duration of last tick's AMEC state
- if(l_last_state >= NUM_AMEC_SMH_STATES)
- {
- // Sanity check. Trace this out, even though it should never happen.
- TRAC_INFO("AMEC State Invalid, Sensor Not Updated");
- }
- else
- {
- // AMESSdurX = duration of last tick's AMEC state
- sensor_update( AMECSENSOR_ARRAY_PTR(AMESSdur0, l_last_state), G_fw_timing.amess_dur);
- }
+ gpe_gpenxiramdbg_t xsr_sprg0 = {0};
+ gpe_gpenxiramedr_t ir_edr = {0};
+ gpe_gpenxidbgpro_t iar_xsr = {0};
// ------------------------------------------------------
// Kick off GPE programs to track WorstCase time in GPE
// and update the sensors.
// ------------------------------------------------------
- if( (NULL != G_fw_timing.gpe0_timing_request) &&
- (NULL != G_fw_timing.gpe1_timing_request) )
+ if(NULL != G_fw_timing.gpe0_timing_request)
{
- //Check if both GPE engines were able to complete the last GPE job on
- //the queue within 1 tick.
+ //Check if GPE0 was able to complete the last GPE job within 1 tick
l_gpe0_idle = async_request_is_idle(&G_fw_timing.gpe0_timing_request->request);
- l_gpe1_idle = async_request_is_idle(&G_fw_timing.gpe1_timing_request->request);
- if(l_gpe0_idle && l_gpe1_idle)
+ if(l_gpe0_idle)
{
- //reset the consecutive trace counts
+ //reset the consecutive trace count
L_consec_trace_count[0] = 0;
- L_consec_trace_count[1] = 0;
- //Both GPE engines finished on time. Now check if they were
- //successful too.
- if( async_request_completed(&(G_fw_timing.gpe0_timing_request->request)) &&
- async_request_completed(&(G_fw_timing.gpe1_timing_request->request)) )
+ //Now check if successful too.
+ if( async_request_completed(&(G_fw_timing.gpe0_timing_request->request)) )
{
// GPEtickdur0 = duration of last tick's PORE-GPE0 duration
sensor_update( AMECSENSOR_PTR(GPEtickdur0), G_fw_timing.gpe_dur[0]);
- // GPEtickdur1 = duration of last tick's PORE-GPE1 duration
- sensor_update( AMECSENSOR_PTR(GPEtickdur1), G_fw_timing.gpe_dur[1]);
}
- else
+ //This case is expected on the first call of the function.
+ //After that, this should not happen.
+ else if(!L_first_call)
{
- //This case is expected on the first call of the function.
- //After that, this should not happen.
- if(!l_first_call)
- {
- //Note: FFDC for this case is gathered by each task
- //responsible for a GPE job.
- TRAC_INFO("GPE task idle but GPE task did not complete");
- }
- l_first_call = FALSE;
+ //Note: FFDC for this case is gathered by each task
+ //responsible for a GPE job.
+ TRAC_INFO("GPE0 task idle but GPE0 task did not complete");
}
- // Update Time used to measure GPE duration.
- G_fw_timing.rtl_start_gpe = G_fw_timing.rtl_start;
-
// Schedule the GPE Routines that will run and update the worst
// case timings (via callback) after they complete. These GPE
// routines are the last GPE routines added to the queue
// during the RTL tick.
+ G_fw_timing.rtl_start_gpe[0] = G_fw_timing.rtl_start;
rc = gpe_request_schedule(G_fw_timing.gpe0_timing_request);
- rc2 = gpe_request_schedule(G_fw_timing.gpe1_timing_request);
-
- if(rc || rc2)
- {
- /* @
- * @errortype
- * @moduleid AMEC_UPDATE_FW_SENSORS
- * @reasoncode SSX_GENERIC_FAILURE
- * @userdata1 return code - gpe0
- * @userdata2 return code - gpe1
- * @userdata4 OCC_NO_EXTENDED_RC
- * @devdesc Failure to schedule PORE-GPE poreFlex object for FW timing
- * analysis.
- */
- l_err = createErrl(
- AMEC_UPDATE_FW_SENSORS, //modId
- SSX_GENERIC_FAILURE, //reasoncode
- OCC_NO_EXTENDED_RC, //Extended reason code
- ERRL_SEV_INFORMATIONAL, //Severity
- NULL, //Trace Buf
- DEFAULT_TRACE_SIZE, //Trace Size
- rc, //userdata1
- rc2); //userdata2
-
- // commit error log
- commitErrl( &l_err );
- }
}
else
{
- gpe_gpenxiramdbg_t xsr_sprg0 = {0};
- gpe_gpenxiramedr_t ir_edr = {0};
- gpe_gpenxidbgpro_t iar_xsr = {0};
-
// Reset will eventually be requested due to not having power measurement
// data after X ticks, but add some additional FFDC to the trace that
// will tell us what GPE job is currently executing.
- if(!l_gpe0_idle)
+ INCREMENT_ERR_HISTORY(ERRH_GPE0_NOT_IDLE);
+
+ if(L_consec_trace_count[0] < MAX_CONSEC_TRACE)
{
- INCREMENT_ERR_HISTORY(ERRH_GPE0_NOT_IDLE);
+ xsr_sprg0.fields.xsr = in32(GPE_GPE0XIXSR);
+ xsr_sprg0.fields.sprg0 = in32(GPE_GPE0XISPRG0);
+ ir_edr.fields.edr = in32(GPE_GPE0XIEDR);
+ ir_edr.fields.ir = in32(GPE_GPE0XIIR);
+ iar_xsr.fields.iar = in32(GPE_GPE0XIIAR);
+ TRAC_ERR("GPE0 programs did not complete within one tick. "
+ "XSR[0x%08x] IAR[0x%08x] IR[0x%08x] EDR[0x%08x] SPRG0[0x%08X]",
+ xsr_sprg0.fields.xsr, iar_xsr.fields.iar,
+ ir_edr.fields.ir, ir_edr.fields.edr, xsr_sprg0.fields.sprg0);
+ L_consec_trace_count[0]++;
+ }
+ }
+
+ }
+ if(NULL != G_fw_timing.gpe1_timing_request)
+ {
+ //Check if GPE1 was able to complete the last GPE job within 1 tick
+ l_gpe1_idle = async_request_is_idle(&G_fw_timing.gpe1_timing_request->request);
+
+ if(l_gpe1_idle)
+ {
+ //reset the consecutive trace count
+ L_consec_trace_count[1] = 0;
- if(L_consec_trace_count[0] < MAX_CONSEC_TRACE)
- {
- xsr_sprg0.fields.xsr = in32(GPE_GPE0XIXSR);
- xsr_sprg0.fields.sprg0 = in32(GPE_GPE0XISPRG0);
- ir_edr.fields.edr = in32(GPE_GPE0XIEDR);
- ir_edr.fields.ir = in32(GPE_GPE0XIIR);
- iar_xsr.fields.iar = in32(GPE_GPE0XIIAR);
- TRAC_ERR("GPE0 programs did not complete within one tick. "
- "XSR[0x%08x] IAR[0x%08x] IR[0x%08x] EDR[0x%08x] SPRG0[0x%08X]",
- xsr_sprg0.fields.xsr, iar_xsr.fields.iar,
- ir_edr.fields.ir, ir_edr.fields.edr, xsr_sprg0.fields.sprg0);
- L_consec_trace_count[0]++;
- }
+ //Now check if successful too.
+ if( async_request_completed(&(G_fw_timing.gpe1_timing_request->request)) )
+ {
+ // GPEtickdur1 = duration of last tick's PORE-GPE1 duration
+ sensor_update( AMECSENSOR_PTR(GPEtickdur1), G_fw_timing.gpe_dur[1]);
}
- else
+ //This case is expected on the first call of the function.
+ //After that, this should not happen.
+ else if(!L_first_call)
{
- L_consec_trace_count[0] = 0;
+ //Note: FFDC for this case is gathered by each task
+ //responsible for a GPE job.
+ TRAC_INFO("GPE1 task idle but GPE1 task did not complete");
}
- if(!l_gpe1_idle)
- {
- INCREMENT_ERR_HISTORY(ERRH_GPE1_NOT_IDLE);
+ // Schedule the GPE Routines that will run and update the worst
+ // case timings (via callback) after they complete. These GPE
+ // routines are the last GPE routines added to the queue
+ // during the RTL tick.
+ G_fw_timing.rtl_start_gpe[1] = G_fw_timing.rtl_start;
+ rc2 = gpe_request_schedule(G_fw_timing.gpe1_timing_request);
- if(L_consec_trace_count[1] < MAX_CONSEC_TRACE)
- {
- xsr_sprg0.fields.xsr = in32(GPE_GPE1XIXSR);
- xsr_sprg0.fields.sprg0 = in32(GPE_GPE1XISPRG0);
- ir_edr.fields.edr = in32(GPE_GPE1XIEDR);
- ir_edr.fields.ir = in32(GPE_GPE1XIIR);
- iar_xsr.fields.iar = in32(GPE_GPE1XIIAR);
- TRAC_ERR("GPE1 programs did not complete within one tick. "
- "XSR[0x%08x] IAR[0x%08x] IR[0x%08x] EDR[0x%08x] SPRG0[0x%08X]",
- xsr_sprg0.fields.xsr, iar_xsr.fields.iar,
- ir_edr.fields.ir, ir_edr.fields.edr, xsr_sprg0.fields.sprg0);
- L_consec_trace_count[1]++;
- }
- }
- else
+ }
+ else
+ {
+ INCREMENT_ERR_HISTORY(ERRH_GPE1_NOT_IDLE);
+
+ if(L_consec_trace_count[1] < MAX_CONSEC_TRACE)
{
- L_consec_trace_count[1] = 0;
+ xsr_sprg0.fields.xsr = in32(GPE_GPE1XIXSR);
+ xsr_sprg0.fields.sprg0 = in32(GPE_GPE1XISPRG0);
+ ir_edr.fields.edr = in32(GPE_GPE1XIEDR);
+ ir_edr.fields.ir = in32(GPE_GPE1XIIR);
+ iar_xsr.fields.iar = in32(GPE_GPE1XIIAR);
+ TRAC_ERR("GPE1 programs did not complete within one tick. "
+ "XSR[0x%08x] IAR[0x%08x] IR[0x%08x] EDR[0x%08x] SPRG0[0x%08X]",
+ xsr_sprg0.fields.xsr, iar_xsr.fields.iar,
+ ir_edr.fields.ir, ir_edr.fields.edr, xsr_sprg0.fields.sprg0);
+ L_consec_trace_count[1]++;
}
}
}
+ if(rc || rc2)
+ {
+ /* @
+ * @errortype
+ * @moduleid AMEC_UPDATE_FW_SENSORS
+ * @reasoncode SSX_GENERIC_FAILURE
+ * @userdata1 return code - gpe0
+ * @userdata2 return code - gpe1
+ * @userdata4 OCC_NO_EXTENDED_RC
+ * @devdesc Failure to schedule PORE-GPE poreFlex object for FW timing
+ * analysis.
+ */
+ l_err = createErrl(
+ AMEC_UPDATE_FW_SENSORS, //modId
+ SSX_GENERIC_FAILURE, //reasoncode
+ OCC_NO_EXTENDED_RC, //Extended reason code
+ ERRL_SEV_INFORMATIONAL, //Severity
+ NULL, //Trace Buf
+ DEFAULT_TRACE_SIZE, //Trace Size
+ rc, //userdata1
+ rc2); //userdata2
+
+ // commit error log
+ commitErrl( &l_err );
+ }
+
+ L_first_call = FALSE;
+}
+
+
+// Function Specification
+//
+// Name: amec_update_fw_sensors
+//
+// Description: Updates sensors related to the OCC FW Timings
+//
+// Thread: RealTime Loop
+//
+// End Function Specification
+#define MAX_CONSEC_TRACE 4
+void amec_update_fw_sensors(void)
+{
+ // ------------------------------------------------------
+ // Update OCC Firmware Sensors from last tick
+ // ------------------------------------------------------
+ int l_last_state = G_fw_timing.amess_state;
+ // RTLtickdur = duration of last tick's RTL ISR (max = 250us)
+ sensor_update( AMECSENSOR_PTR(RTLtickdur), G_fw_timing.rtl_dur);
+ // AMEintdur = duration of last tick's AMEC portion of RTL ISR
+ sensor_update( AMECSENSOR_PTR(AMEintdur), G_fw_timing.ameint_dur);
+ // AMESSdurX = duration of last tick's AMEC state
+ if(l_last_state >= NUM_AMEC_SMH_STATES)
+ {
+ // Sanity check. Trace this out, even though it should never happen.
+ TRAC_INFO("AMEC State Invalid, Sensor Not Updated");
+ }
+ else
+ {
+ // AMESSdurX = duration of last tick's AMEC state
+ sensor_update( AMECSENSOR_ARRAY_PTR(AMESSdur0, l_last_state), G_fw_timing.amess_dur);
+ }
}
/*----------------------------------------------------------------------------*/
OpenPOWER on IntegriCloud