diff options
author | Wael El-Essawy <welessa@us.ibm.com> | 2016-09-16 10:18:30 -0500 |
---|---|---|
committer | Wael El-Essawy <welessa@us.ibm.com> | 2016-09-23 16:04:11 -0400 |
commit | d137bd848a05d5afd8a9ee5c9803f421ebd0a922 (patch) | |
tree | 75fa87939a9f7028921504e9b6a27cbd138af930 /src | |
parent | a1788a7353ef2072534b77f79396c04ade749314 (diff) | |
download | talos-occ-d137bd848a05d5afd8a9ee5c9803f421ebd0a922.tar.gz talos-occ-d137bd848a05d5afd8a9ee5c9803f421ebd0a922.zip |
Enable FW Timing Sensors
Enable scheduling of the GPE NOP task to do GPE timings and verify all
sensors being updated in amec_update_fw_sensors() are being populated correctly.
Change-Id: I623dd7518be9a8736e601c7d2fa748097a4d773a
RTC: 141299
Reviewed-on: http://ralgit01.raleigh.ibm.com/gerrit1/29849
Tested-by: FSP CI Jenkins <fsp-CI-jenkins+hostboot@us.ibm.com>
Reviewed-by: Wael El-Essawy <welessa@us.ibm.com>
Diffstat (limited to 'src')
-rwxr-xr-x | src/gpe_export.h | 7 | ||||
-rw-r--r-- | src/ipc_func_ids.h | 2 | ||||
-rw-r--r-- | src/occ_405/amec/amec_init.c | 42 | ||||
-rw-r--r-- | src/occ_405/amec/amec_sensors_fw.c | 68 | ||||
-rwxr-xr-x | src/occ_405/dimm/dimm.c | 6 | ||||
-rw-r--r-- | src/occ_gpe0/gpe_util.c | 30 | ||||
-rw-r--r-- | src/occ_gpe0/ipc_func_tables.c | 4 | ||||
-rw-r--r-- | src/occ_gpe1/gpe1_main.c | 1 | ||||
-rw-r--r-- | src/occ_gpe1/ipc_func_tables.c | 3 | ||||
-rw-r--r-- | src/occ_gpe1/nop.c | 61 | ||||
-rw-r--r-- | src/occ_gpe1/topfiles.mk | 2 |
11 files changed, 158 insertions, 68 deletions
diff --git a/src/gpe_export.h b/src/gpe_export.h index 7f4496d..9c53f77 100755 --- a/src/gpe_export.h +++ b/src/gpe_export.h @@ -44,11 +44,16 @@ typedef struct { // Arguments for doing a SCOM from GPE0 typedef struct ipc_scom_op { + GpeErrorStruct error; // Error of SCOM operation uint32_t addr; // Register address uint64_t data; // Data for read/write uint32_t size; // Size of data buffer uint8_t read; // Read (1) or write (0) - GpeErrorStruct error; // Error of SCOM operation } ipc_scom_op_t; +typedef struct nop +{ + GpeErrorStruct error; // Error of operation +} nop_t; + #endif //_GPE_EXPORT_H diff --git a/src/ipc_func_ids.h b/src/ipc_func_ids.h index f640674..b5d446f 100644 --- a/src/ipc_func_ids.h +++ b/src/ipc_func_ids.h @@ -57,6 +57,7 @@ IPC_FUNCIDS_TABLE_START IPC_FUNC_ID(IPC_ST_APSS_COMPLETE_PWR_MEAS_READ_FUNCID) IPC_FUNC_ID(IPC_ST_GET_CORE_DATA_FUNCID) IPC_FUNC_ID(IPC_ST_SCOM_OPERATION) + IPC_FUNC_ID(IPC_ST_GPE0_NOP) IPC_FUNCIDS_ST_END(OCCHW_INST_ID_GPE0) //Functions that are only supported by GPE1 should be defined here @@ -64,6 +65,7 @@ IPC_FUNCIDS_TABLE_START IPC_FUNCIDS_ST_START(OCCHW_INST_ID_GPE1) IPC_FUNC_ID(IPC_ST_DIMM_SM_FUNCID) IPC_FUNC_ID(IPC_ST_DIMM_CONTROL_FUNCID) + IPC_FUNC_ID(IPC_ST_GPE1_NOP) IPC_FUNCIDS_ST_END(OCCHW_INST_ID_GPE1) //Functions that are only supported by GPE2 should be defined here diff --git a/src/occ_405/amec/amec_init.c b/src/occ_405/amec/amec_init.c index 4179e70..e0fdd84 100644 --- a/src/occ_405/amec/amec_init.c +++ b/src/occ_405/amec/amec_init.c @@ -357,41 +357,37 @@ void amec_init_gamec_struct(void) // End Function Specification void amec_slave_init() { -// @TODO - TEMP: not ready yet -/* errlHndl_t l_err = NULL; // Error handler int rc = 0; // Return code int rc2 = 0; // Return code -*/ // Set the GPE Request Pointers to NULL in case the create fails. G_fw_timing.gpe0_timing_request = NULL; G_fw_timing.gpe1_timing_request = NULL; -// @TODO - TEMP: not ready yet -#if 0 - // Initializes the GPE routine that will be used to measure the worst case // timings for GPE0 - rc = pore_flex_create( &G_gpe_nop_request[0], //gpe_req for the task - &G_pore_gpe0_queue, //queue - (void *) GPE_pore_nop, //entry point - (uint32_t) NULL, //parm for the task - SSX_WAIT_FOREVER, //no timeout - (AsyncRequestCallback) amec_slv_update_gpe_sensors, //callback - (void *) GPE_ENGINE_0, //callback argument - ASYNC_CALLBACK_IMMEDIATE ); //options + rc = gpe_request_create(&G_gpe_nop_request[0], //gpe_req for the task + &G_async_gpe_queue0, //queue + IPC_ST_GPE0_NOP, //Function ID + NULL, //parm for the task + SSX_WAIT_FOREVER, //no timeout + (AsyncRequestCallback) + amec_slv_update_gpe_sensors, //callback + (void *) GPE_ENGINE_0, //callback argument + ASYNC_CALLBACK_IMMEDIATE ); //options // Initializes the GPE routine that will be used to measure the worst case // timings for GPE1 - rc2 = pore_flex_create( &G_gpe_nop_request[1], //gpe_req for the task - &G_pore_gpe1_queue, //queue - (void *)GPE_pore_nop, //entry point - (uint32_t) NULL, //parm for the task - SSX_WAIT_FOREVER, //no timeout - (AsyncRequestCallback) amec_slv_update_gpe_sensors, //callback - (void *) GPE_ENGINE_1, //callback argument - ASYNC_CALLBACK_IMMEDIATE ); //options + rc2 = gpe_request_create( &G_gpe_nop_request[1], //gpe_req for the task + &G_async_gpe_queue1, //queue + IPC_ST_GPE1_NOP, //Function ID + NULL, //parm for the task + SSX_WAIT_FOREVER, //no timeout + (AsyncRequestCallback) + amec_slv_update_gpe_sensors, //callback + (void *) GPE_ENGINE_1, //callback argument + ASYNC_CALLBACK_IMMEDIATE ); //options // If we couldn't create the poreFlex objects, there must be a major problem // so we will log an error and halt OCC. @@ -432,8 +428,6 @@ void amec_slave_init() G_fw_timing.gpe1_timing_request = &G_gpe_nop_request[1]; } -#endif // #if 0 - @TODO - TEMP - Not ready yet - // Initialize Vector Sensors for AMEC use amec_init_vector_sensors(); diff --git a/src/occ_405/amec/amec_sensors_fw.c b/src/occ_405/amec/amec_sensors_fw.c index 8447f2c..07b3f5d 100644 --- a/src/occ_405/amec/amec_sensors_fw.c +++ b/src/occ_405/amec/amec_sensors_fw.c @@ -42,6 +42,8 @@ #include "sensor_enum.h" #include "amec_service_codes.h" #include <amec_sensors_fw.h> +#include "gpe_register_addresses.h" +#include "gpe_firmware_registers.h" /******************************************************************************/ /* Globals */ @@ -124,13 +126,14 @@ void amec_update_fw_sensors(void) // 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) && + (NULL != G_fw_timing.gpe1_timing_request) ) { //Check if both GPE engines were able to complete the last GPE job on //the queue 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) { //reset the consecutive trace count @@ -138,8 +141,8 @@ void amec_update_fw_sensors(void) //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)) ) + if( async_request_completed(&(G_fw_timing.gpe0_timing_request->request)) && + async_request_completed(&(G_fw_timing.gpe1_timing_request->request)) ) { // GPEtickdur0 = duration of last tick's PORE-GPE0 duration sensor_update( AMECSENSOR_PTR(GPEtickdur0), G_fw_timing.gpe_dur[0]); @@ -162,15 +165,13 @@ void amec_update_fw_sensors(void) // Update Time used to measure GPE duration. G_fw_timing.rtl_start_gpe = G_fw_timing.rtl_start; -// @TODO - TEMP - Old PORE SCHEDULE, needs to be replaced with GPE schedule code. -/* // 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. - rc = pore_flex_schedule(G_fw_timing.gpe0_timing_request); - rc2 = pore_flex_schedule(G_fw_timing.gpe1_timing_request); -*/ + rc = gpe_request_schedule(G_fw_timing.gpe0_timing_request); + rc2 = gpe_request_schedule(G_fw_timing.gpe1_timing_request); + if(rc || rc2) { /* @ @@ -199,45 +200,38 @@ void amec_update_fw_sensors(void) } else if(L_consec_trace_count < MAX_CONSEC_TRACE) { -// @TODO: TEMP - PORE GPE Codes, needs to reflect PPE architecture. -/* - uint64_t l_dbg0; - uint64_t l_dbg1; - uint64_t l_status; + gpe_gpenxiramdbg_t xsr_sprg0; + gpe_gpenxiramedr_t ir_edr; + gpe_gpenxidbgpro_t iar_xsr; // 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) { - l_dbg1 = in64(PORE_GPE0_DBG1); - l_dbg0 = in64(PORE_GPE0_DBG0); - l_status = in64(PORE_GPE0_STATUS); - TRAC_ERR("GPE0 programs did not complete within one tick. DBG0[0x%08x%08x] DBG1[0x%08x%08x]", - (uint32_t)(l_dbg0 >> 32), - (uint32_t)(l_dbg0 & 0x00000000ffffffffull), - (uint32_t)(l_dbg1 >> 32), - (uint32_t)(l_dbg1 & 0x00000000ffffffffull)); - TRAC_ERR("Additional GPE0 debug data: STATUS[0x%08x%08x]", - (uint32_t)(l_status >> 32), - (uint32_t)(l_status & 0x00000000ffffffffull)); + xsr_sprg0.value = in64(GPE_GPE0XIRAMDBG); + ir_edr.value = in64(GPE_GPE0XIRAMEDR); + iar_xsr.value = in64(GPE_GPE0XIDBGPRO); + TRAC_ERR("GPE0 programs did not complete within one tick. " + "XSR[0x%08x] IAR[0x%08x] IR[0x%08x] EDR[0x%08x]", + iar_xsr.fields.xsr, iar_xsr.fields.iar, + ir_edr.fields.ir, ir_edr.fields.edr); + TRAC_ERR("Additional GPE0 debug data: RAM_XSR[0x%08x] RAM_SPRG0[0x%08x]", + xsr_sprg0.fields.xsr, xsr_sprg0.fields.sprg0); } if(!l_gpe1_idle) { - l_dbg1 = in64(PORE_GPE1_DBG1); - l_dbg0 = in64(PORE_GPE1_DBG0); - l_status = in64(PORE_GPE1_STATUS); - TRAC_ERR("GPE1 programs did not complete within one tick. DBG0[0x%08x%08x] DBG1[0x%08x%08x]", - (uint32_t)(l_dbg0 >> 32), - (uint32_t)(l_dbg0 & 0x00000000ffffffffull), - (uint32_t)(l_dbg1 >> 32), - (uint32_t)(l_dbg1 & 0x00000000ffffffffull)); - TRAC_ERR("Additional GPE1 debug data: STATUS[0x%08x%08x]", - (uint32_t)(l_status >> 32), - (uint32_t)(l_status & 0x00000000ffffffffull)); + xsr_sprg0.value = in64(GPE_GPE1XIRAMDBG); + ir_edr.value = in64(GPE_GPE1XIRAMEDR); + iar_xsr.value = in64(GPE_GPE1XIDBGPRO); + TRAC_ERR("GPE1 programs did not complete within one tick. " + "XSR[0x%08x] IAR[0x%08x] IR[0x%08x] EDR[0x%08x]", + iar_xsr.fields.xsr, iar_xsr.fields.iar, + ir_edr.fields.ir, ir_edr.fields.edr); + TRAC_ERR("Additional GPE1 debug data: RAM_XSR[0x%08x] RAM_SPRG0[0x%08x]", + xsr_sprg0.fields.xsr, xsr_sprg0.fields.sprg0); } L_consec_trace_count++; -*/ } } } diff --git a/src/occ_405/dimm/dimm.c b/src/occ_405/dimm/dimm.c index 62250da..676f127 100755 --- a/src/occ_405/dimm/dimm.c +++ b/src/occ_405/dimm/dimm.c @@ -142,10 +142,10 @@ void memory_nimbus_init() // Initializes GPE request for DIMM temperature reading IPC Task, DIMM_DBG("memory_nimbus_init: Creating request GPE1 DIMM data IPC task"); rc_dimm_sm = gpe_request_create( - &G_dimm_sm_request, + &G_dimm_sm_request, // gpe_req for the task &G_async_gpe_queue1, // queue - IPC_ST_DIMM_SM_FUNCID, // entry_point - &G_dimm_sm_args, // entry_point arg + IPC_ST_DIMM_SM_FUNCID, // Function ID + &G_dimm_sm_args, // parm for the task SSX_WAIT_FOREVER, // no timeout NULL, // callback NULL, // callback arg diff --git a/src/occ_gpe0/gpe_util.c b/src/occ_gpe0/gpe_util.c index d8f7e6d..72a0288 100644 --- a/src/occ_gpe0/gpe_util.c +++ b/src/occ_gpe0/gpe_util.c @@ -216,3 +216,33 @@ void ipc_scom_operation(ipc_msg_t* cmd, void* arg) pk_halt(); } } + +/* + * Function Specification: + * + * Name: gpe0_nop + * + * Description: a function that does nothing. Called to measure IPC timing + * + * Inputs: none + * + * return: none + * + * End Function Specification + */ + +void gpe0_nop(ipc_msg_t* cmd, void* arg) +{ + int rc; + ipc_async_cmd_t *async_cmd = (ipc_async_cmd_t*)cmd; + nop_t *args = (nop_t*)async_cmd->cmd_data; + + // send back a response, IPC success even if ffdc/rc are non zeros + rc = ipc_send_rsp(cmd, IPC_RC_SUCCESS); + if(rc) + { + PK_TRACE("gpe0_nop: Failed to send response back. Halting GPE0", rc); + gpe_set_ffdc(&(args->error), 0x00, GPE_RC_IPC_SEND_FAILED, rc); + pk_halt(); + } +} diff --git a/src/occ_gpe0/ipc_func_tables.c b/src/occ_gpe0/ipc_func_tables.c index afb399b..7b4c8a1 100644 --- a/src/occ_gpe0/ipc_func_tables.c +++ b/src/occ_gpe0/ipc_func_tables.c @@ -36,6 +36,8 @@ void gpe_get_core_data(ipc_msg_t* cmd, void* arg); void ipc_scom_operation(ipc_msg_t* cmd, void* arg); +void gpe0_nop(ipc_msg_t* cmd, void* arg); + extern ipc_msgq_t G_gpe0_test_msgq0; // Function table for multi target (common) functions @@ -66,7 +68,7 @@ IPC_HANDLER(apss_continue_pwr_meas_read, 0) // 4 - IPC_ST_APSS_CONTINUE_PWR_MEA IPC_HANDLER(apss_complete_pwr_meas_read, 0) // 5 - IPC_ST_APSS_COMPLETE_PWR_MEAS_READ_FUNCID IPC_HANDLER(gpe_get_core_data, 0) // 6 - IPC_ST_GET_CORE_DATA_FUNCID IPC_HANDLER(ipc_scom_operation, 0) // 7 - IPC_ST_SCOM_OPERATION -IPC_HANDLER_DEFAULT // 8 +IPC_HANDLER(gpe0_nop, 0) // 8 - IPC_ST_GPE0_NOP IPC_HANDLER_DEFAULT // 9 IPC_HANDLER_DEFAULT // 10 IPC_HANDLER_DEFAULT // 11 diff --git a/src/occ_gpe1/gpe1_main.c b/src/occ_gpe1/gpe1_main.c index 88f3be8..a7a3ff5 100644 --- a/src/occ_gpe1/gpe1_main.c +++ b/src/occ_gpe1/gpe1_main.c @@ -69,3 +69,4 @@ int main(int argc, char **argv) return 0; } + diff --git a/src/occ_gpe1/ipc_func_tables.c b/src/occ_gpe1/ipc_func_tables.c index ab352c6..d575ae3 100644 --- a/src/occ_gpe1/ipc_func_tables.c +++ b/src/occ_gpe1/ipc_func_tables.c @@ -26,6 +26,7 @@ #include "gpe1_dimm.h" void gpe_dimm_control(ipc_msg_t* cmd, void* arg); +void gpe1_nop(ipc_msg_t* cmd, void* arg); // Function table for multi target (common) functions IPC_MT_FUNC_TABLE_START @@ -43,7 +44,7 @@ IPC_MT_FUNC_TABLE_END IPC_ST_FUNC_TABLE_START IPC_HANDLER(gpe_dimm_sm, 0) // 0 - IPC_ST_DIMM_SM_FUNCID IPC_HANDLER(gpe_dimm_control, 0) // 1 - IPC_ST_DIMM_CONTROL_FUNCID -IPC_HANDLER_DEFAULT // 2 +IPC_HANDLER(gpe1_nop, 0) // 2 - IPC_ST_GPE1_NOP IPC_HANDLER_DEFAULT // 3 IPC_HANDLER_DEFAULT // 4 IPC_HANDLER_DEFAULT // 5 diff --git a/src/occ_gpe1/nop.c b/src/occ_gpe1/nop.c new file mode 100644 index 0000000..5a99c64 --- /dev/null +++ b/src/occ_gpe1/nop.c @@ -0,0 +1,61 @@ +/* IBM_PROLOG_BEGIN_TAG */ +/* This is an automatically generated prolog. */ +/* */ +/* $Source: src/occ_gpe1/nop.c $ */ +/* */ +/* OpenPOWER OnChipController Project */ +/* */ +/* Contributors Listed Below - COPYRIGHT 2015,2016 */ +/* [+] 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 */ + +#include "pk.h" +#include "ppe42_scom.h" +#include "gpe_export.h" +#include "ipc_api.h" +#include "ipc_async_cmd.h" +#include "gpe_util.h" + +/* + * Function Specification: + * + * Name: gpe1_nop + * + * Description: a function that does nothing. Called to measure IPC timing + * + * Inputs: none + * + * return: none + * + * End Function Specification + */ + +void gpe1_nop(ipc_msg_t* cmd, void* arg) +{ + int rc; + ipc_async_cmd_t *async_cmd = (ipc_async_cmd_t*)cmd; + nop_t *args = (nop_t*)async_cmd->cmd_data; + + // send back a response, IPC success even if ffdc/rc are non zeros + rc = ipc_send_rsp(cmd, IPC_RC_SUCCESS); + if(rc) + { + PK_TRACE("gpe1_nop: Failed to send response back. Halting GPE1", rc); + gpe_set_ffdc(&(args->error), 0x00, GPE_RC_IPC_SEND_FAILED, rc); + pk_halt(); + } +} diff --git a/src/occ_gpe1/topfiles.mk b/src/occ_gpe1/topfiles.mk index 4499c81..75a8fbc 100644 --- a/src/occ_gpe1/topfiles.mk +++ b/src/occ_gpe1/topfiles.mk @@ -23,7 +23,7 @@ # # IBM_PROLOG_END_TAG -TOP-C-SOURCES = gpe1_main.c gpe1_dimm_read.c gpe1_dimm_reset.c \ +TOP-C-SOURCES = gpe1_main.c gpe1_dimm_read.c gpe1_dimm_reset.c nop.c \ pk_app_irq_table.c ipc_func_tables.c gpe1_dimm_control.c TOP-S-SOURCES = |