Beispiel #1
0
/// @brief Platform-level implementation of modifyCfamRegister()
ReturnCode platModifyCfamRegister(const Target<TARGET_TYPE_ALL>& i_target,
                                  const uint32_t i_address,
                                  const buffer<uint32_t> i_data,
                                  const ChipOpModifyMode i_modifyMode)
{
    FAPI_DBG(ENTER_MRK "platModifyCfamRegister");
    ReturnCode l_rc;
    errlHndl_t l_err = NULL;
    bool l_traceit = platIsScanTraceEnabled();
    const char* l_modeString = platModeString(i_modifyMode);

    // Grab the name of the target
    TARGETING::ATTR_FAPI_NAME_type l_targName = {0};
    fapi2::toString(i_target, l_targName, sizeof(l_targName));

    do
    {
        // Can't access cfam engine on master processor
        l_err = verifyCfamAccessTarget(i_target,i_address);
        if (l_err)
        {
            FAPI_ERR("platModifyCfamRegister: verifyCfamAccessTarget returns error!");
            l_rc.setPlatDataPtr(reinterpret_cast<void *> (l_err));
            break;
        }

        // Extract the component pointer
        TARGETING::Target* l_target =
                reinterpret_cast<TARGETING::Target*>(i_target.get());

        // Get the chip target if l_target is not a chip
        TARGETING::Target* l_myChipTarget = NULL;
        l_err = getCfamChipTarget(l_target, l_myChipTarget);
        if (l_err)
        {
            FAPI_ERR("platModifyCfamRegister: getCfamChipTarget returns error!");
            l_rc.setPlatDataPtr(reinterpret_cast<void *> (l_err));
            break;
        }

        // Read current value
        // Address needs to be multiply by 4 because register addresses are word
        // offsets but the FSI addresses are byte offsets.
        // However, we need to preserve the engine's offset of 0x0C00 and 0x1000
        uint64_t l_addr = ((i_address & CFAM_ADDRESS_MASK) << 2) |
            (i_address & CFAM_ENGINE_OFFSET);
        buffer<uint32_t> l_data = 0;
        size_t l_size = sizeof(uint32_t);
        l_err = deviceRead(l_myChipTarget,
                           &l_data(),
                           l_size,
                           DEVICE_FSI_ADDRESS(l_addr));
        if (l_err)
        {
            FAPI_ERR("platModifyCfamRegister: deviceRead returns error!");
            l_rc.setPlatDataPtr(reinterpret_cast<void *> (l_err));
            break;
        }

        // Applying modification
        platProcess32BitModifyMode(i_modifyMode, i_data, l_data);

        // Write back
        l_err = deviceWrite(l_target,
                            &l_data(),
                            l_size,
                            DEVICE_FSI_ADDRESS(l_addr));
        if (l_err)
        {
            FAPI_ERR("platModifyCfamRegister: deviceWrite returns error!");
            l_rc.setPlatDataPtr(reinterpret_cast<void *> (l_err));
            break;
        }

    } while (0);

    if (l_rc != fapi2::FAPI2_RC_SUCCESS)
    {
        FAPI_ERR("platModifyCfamRegister failed - Target %s, Addr %.8X",
                  l_targName, i_address);
    }

    if( l_traceit )
    {
        uint32_t l_data = (uint32_t)i_data;
        FAPI_SCAN( "TRACE : MODCFAMREG  : %s : %.8X %.8X %s",
                   l_targName,
                   i_address,
                   l_data,
                   l_modeString );
    }

    FAPI_DBG(EXIT_MRK "platModifyCfamRegister");
    return l_rc;
}
Beispiel #2
0
/// @brief Platform-level implementation called by getCfamRegister()
ReturnCode platGetCfamRegister(const Target<TARGET_TYPE_ALL>& i_target,
                               const uint32_t i_address,
                               buffer<uint32_t>& o_data)
{
    FAPI_DBG(ENTER_MRK "platGetCfamRegister");
    ReturnCode l_rc;
    errlHndl_t l_err = NULL;
    bool l_traceit = platIsScanTraceEnabled();

    // Grab the name of the target
    TARGETING::ATTR_FAPI_NAME_type l_targName = {0};
    fapi2::toString(i_target, l_targName, sizeof(l_targName));

    do
    {
        // Extract the target pointer
        TARGETING::Target* l_target =
                reinterpret_cast<TARGETING::Target*>(i_target.get());

        // Get the chip target if l_target is not a chip
        TARGETING::Target* l_myChipTarget = NULL;
        l_err = getCfamChipTarget(l_target, l_myChipTarget);
        if (l_err)
        {
            FAPI_ERR("platGetCfamRegister: getCfamChipTarget returns error!");
            FAPI_ERR("fapiGetCfamRegister failed - Target %s, Addr %.8X",
                      l_targName, i_address);
            l_rc.setPlatDataPtr(reinterpret_cast<void *> (l_err));
            break;
        }

        // Can't access cfam engine on master processor
        l_err = verifyCfamAccessTarget(i_target,i_address);
        if (l_err)
        {
            FAPI_ERR("platGetCfamRegister: verifyCfamAccessTarget returns error!");
            l_rc.setPlatDataPtr(reinterpret_cast<void *> (l_err));
            break;
        }

        // Perform CFAM read via FSI
        // Address needs to be multiply by 4 because register addresses are
        //  word offsets but the FSI addresses are byte offsets.
        // However, we need to preserve the engine's offset in the top byte
        uint64_t l_addr = ((i_address & CFAM_ADDRESS_MASK) << 2) |
            (i_address & CFAM_ENGINE_OFFSET);
        size_t l_size = sizeof(uint32_t);
        l_err = deviceRead(l_myChipTarget,
                           &o_data(),
                           l_size,
                           DEVICE_FSI_ADDRESS(l_addr));
        if (l_err)
        {
            FAPI_ERR("platGetCfamRegister: deviceRead returns error!");
            l_rc.setPlatDataPtr(reinterpret_cast<void *> (l_err));
            break;
        }

    } while(0);

    if (l_rc != fapi2::FAPI2_RC_SUCCESS)
    {
       FAPI_ERR("fapiGetCfamRegister failed - Target %s, Addr %.8X",
                 l_targName, i_address);
    }

    if( l_traceit )
    {
        uint32_t l_data = (uint32_t)o_data;
        FAPI_SCAN( "TRACE : GETCFAMREG  : %s : %.8X %.8X",
                   l_targName,
                   i_address,
                   l_data);
    }

    FAPI_DBG(EXIT_MRK "platGetCfamRegister");
    return l_rc;
}
Beispiel #3
0
/**
 * @brief Common function to add callouts and FFDC and recover
 *   from PIB errors
 *
 * @param[in]   i_target    SCom target
 * @param[in]   i_errlog    Error log to append to
 * @param[in]   i_status    FSI2PIB status register
 * @param[in]   i_scomAddr  Address that we failed on
 */
void pib_error_handler( TARGETING::Target* i_target,
                        errlHndl_t i_errlog,
                        uint32_t i_status,
                        uint32_t i_scomAddr )
{
    //Add this target to the FFDC
    ERRORLOG::ErrlUserDetailsTarget(i_target,"SCOM Target").addToLog(i_errlog);

    //Look for a totally dead chip
    if( i_status == 0xFFFFFFFF )
    {
        // if things are this broken then chances are there are bigger
        //  problems, we can just make some guesses on what to call out

        // make code the highest since there are other issues
        i_errlog->addProcedureCallout(HWAS::EPUB_PRC_HB_CODE,
                                      HWAS::SRCI_PRIORITY_HIGH);

        // callout this chip as Medium and deconfigure it
        i_errlog->addHwCallout( i_target,
                                HWAS::SRCI_PRIORITY_LOW,
                                HWAS::DELAYED_DECONFIG,
                                HWAS::GARD_NULL );

        // grab all the FFDC we can think of
        FSI::getFsiFFDC( FSI::FFDC_OPB_FAIL_SLAVE,
                         i_errlog,
                         i_target );
        FSI::getFsiFFDC( FSI::FFDC_READWRITE_FAIL,
                         i_errlog,
                         i_target );
        FSI::getFsiFFDC( FSI::FFDC_PIB_FAIL,
                         i_errlog,
                         i_target );
    }
    else
    {
        //Add the callouts for the specific PCB/PIB error
        uint32_t pib_error = i_status >> 12;
        PIB::addFruCallouts( i_target,
                             pib_error,
                             i_scomAddr,
                             i_errlog );

        //Grab the PIB2OPB Status reg for a Resource Occupied error
        if( pib_error == PIB::PIB_RESOURCE_OCCUPIED ) //piberr=001
        {
            FSI::getFsiFFDC( FSI::FFDC_PIB_FAIL,
                             i_errlog,
                             i_target );
        }
    }

    //Recovery sequence from Markus
    //  if SCOM fails and FSI Master displays "MasterTimeOut"
    //     then 7,6  <covered by FSI driver>
    //  else if SCOM fails and FSI2PIB Status shows PIB abort
    //     then just perform unit reset (6) and wait 1 ms
    //  else (PIB_abort='0' but PIB error is unequal 0)
    //     then just perform unit reset (6) (wait not needed).
    uint32_t l_command = 0;
    size_t op_size = sizeof(uint32_t);
    errlHndl_t l_err = DeviceFW::deviceOp( DeviceFW::WRITE,
                                       i_target,
                                       &l_command,
                                       op_size,
                                       DEVICE_FSI_ADDRESS(ENGINE_RESET_REG));
    if(l_err)
    {
        TRACFCOMP( g_trac_fsiscom,
                   ERR_MRK"Error resetting FSI : %.4X",
                   ERRL_GETRC_SAFE(l_err) );
        l_err->plid(i_errlog->plid());
        errlCommit(l_err,FSISCOM_COMP_ID);
    }

    nanosleep( 0,NS_PER_MSEC ); //sleep for ms

}
Beispiel #4
0
void addScomFailFFDC( errlHndl_t i_err,
                      TARGETING::Target* i_target,
                      uint64_t i_addr )
{
    // Read some error regs from scom
    ERRORLOG::ErrlUserDetailsLogRegister l_scom_data(i_target);
    bool addit = false;
    TARGETING::TYPE l_type = TARGETING::TYPE_NA;
    if( i_target == TARGETING::MASTER_PROCESSOR_CHIP_TARGET_SENTINEL )
    {
        l_type = TARGETING::TYPE_PROC;
    }
    else
    {
        l_type = i_target->getAttr<TARGETING::ATTR_TYPE>();
    }

    //PBA scoms on the processor
    if( ((i_addr & 0xFFFFF000) == 0x00064000)
        && (TARGETING::TYPE_PROC == l_type) )
    {
        addit = true;
        //look for hung operations on the PBA
        uint64_t ffdc_regs[] = {
            //grab the PBA buffers in case something is hung
            0x02010850, //PBARBUFVAL0
            0x02010851, //PBARBUFVAL1
            0x02010852, //PBARBUFVAL2
            0x02010858, //PBAWBUFVAL0
            0x02010859, //PBAWBUFVAL1

            0x020F0012, //PB_GP3 (has fence information)
        };
        for( size_t x = 0; x < (sizeof(ffdc_regs)/sizeof(ffdc_regs[0])); x++ )
        {
            l_scom_data.addData(DEVICE_SCOM_ADDRESS(ffdc_regs[x]));
        }
    }
    //EX scoms on the processor (not including PCB slave regs)
    else if( ((i_addr & 0xF0000000) == 0x10000000)
             && ((i_addr & 0x00FF0000) != 0x000F0000)
             && (TARGETING::TYPE_PROC == l_type) )
    {
        addit = true;
        uint64_t ex_offset = 0xFF000000 & i_addr;
        //grab some data related to the PCB slave state
        uint64_t ffdc_regs[] = {
            0x0F010B, //Special Wakeup
            0x0F0012, //GP3
            0x0F0100, //PowerManagement GP0
            0x0F0106, //PFET Status Core
            0x0F010E, //PFET Status ECO
            0x0F0111, //PM State History
        };
        for( size_t x = 0; x < (sizeof(ffdc_regs)/sizeof(ffdc_regs[0])); x++ )
        {
            l_scom_data.addData(DEVICE_SCOM_ADDRESS(ex_offset|ffdc_regs[x]));
        }
    }

    //Any non-PCB Slave and non TP reg on the processor
    if( ((i_addr & 0x00FF0000) != 0x000F0000)
        && ((i_addr & 0xFF000000) != 0x00000000)
        && (TARGETING::TYPE_PROC == l_type) )
    {
        addit = true;
        uint64_t chiplet_offset = 0xFF000000 & i_addr;
        //grab some data related to the PCB slave state
        uint64_t ffdc_regs[] = {
            0x0F0012, //GP3
            0x0F001F, //Error capture reg
        };
        for( size_t x = 0; x < (sizeof(ffdc_regs)/sizeof(ffdc_regs[0])); x++ )
        {
            l_scom_data.addData( DEVICE_SCOM_ADDRESS(
                                 chiplet_offset|ffdc_regs[x]) );
        }

        //grab the clock/osc regs
        l_scom_data.addData(DEVICE_SCOM_ADDRESS(0x00050019));
        l_scom_data.addData(DEVICE_SCOM_ADDRESS(0x0005001A));
        //grab the clock regs via FSI too, just in case
        TARGETING::Target* mproc = NULL;
        TARGETING::targetService().masterProcChipTargetHandle(mproc);
        if( (i_target != TARGETING::MASTER_PROCESSOR_CHIP_TARGET_SENTINEL)
            && (i_target != mproc) )
        {
            l_scom_data.addData(DEVICE_FSI_ADDRESS(0x2864));//==2819
            l_scom_data.addData(DEVICE_FSI_ADDRESS(0x2868));//==281A
        }
    }

    if( addit )
    {
        l_scom_data.addToLog(i_err);
    }
}
Beispiel #5
0
errlHndl_t fsiScomPerformOp(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 = NULL;

    uint64_t l_scomAddr = va_arg(i_args,uint64_t);
    ioData6432 scratchData;
    uint32_t l_command = 0;
    uint32_t l_status = 0;
    bool need_unlock = false;
    size_t op_size = sizeof(uint32_t);
    mutex_t* l_mutex = NULL;

    do{

        if( io_buflen != sizeof(uint64_t) )
        {
            TRACFCOMP( g_trac_fsiscom, ERR_MRK "fsiScomPerformOp> Invalid data length : io_buflen=%d", io_buflen );
            /*@
             * @errortype
             * @moduleid     FSISCOM::MOD_FSISCOM_PERFORMOP
             * @reasoncode   FSISCOM::RC_INVALID_LENGTH
             * @userdata1    SCOM Address
             * @userdata2    Data Length
             * @devdesc      fsiScomPerformOp> 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,
                                            FSISCOM::MOD_FSISCOM_PERFORMOP,
                                            FSISCOM::RC_INVALID_LENGTH,
                                            l_scomAddr,
                                            TO_UINT64(io_buflen));
            l_err->addProcedureCallout( HWAS::EPUB_PRC_HB_CODE,
                                        HWAS::SRCI_PRIORITY_LOW );
            ERRORLOG::ErrlUserDetailsTarget(i_target,"SCOM Target").
              addToLog(l_err);
            break;
        }

        if( (l_scomAddr & 0xFFFFFFFF80000000) != 0)
        {
            TRACFCOMP( g_trac_fsiscom, ERR_MRK "fsiScomPerformOp> Address contains more than 31 bits : l_scomAddr=0x%.16X", l_scomAddr );
            /*@
             * @errortype
             * @moduleid     FSISCOM::MOD_FSISCOM_PERFORMOP
             * @reasoncode   FSISCOM::RC_INVALID_ADDRESS
             * @userdata1    SCOM Address
             * @userdata2    Target HUID
             * @devdesc      fsiScomPerformOp> Address contains
             *               more than 31 bits.
             * @custdesc     A problem occurred during the IPL of the system:
             *               Invalid address on a SCOM operation.
             */
            l_err = new ERRORLOG::ErrlEntry(ERRORLOG::ERRL_SEV_UNRECOVERABLE,
                                            FSISCOM::MOD_FSISCOM_PERFORMOP,
                                            FSISCOM::RC_INVALID_ADDRESS,
                                            l_scomAddr,
                                            TARGETING::get_huid(i_target));
            l_err->addProcedureCallout( HWAS::EPUB_PRC_HB_CODE,
                                        HWAS::SRCI_PRIORITY_LOW );
            ERRORLOG::ErrlUserDetailsTarget(i_target,"SCOM Target").
              addToLog(l_err);
            break;
        }

        l_command = static_cast<uint32_t>(l_scomAddr & 0x000000007FFFFFFF);

        // use the chip-specific mutex attribute
        l_mutex = i_target->getHbMutexAttr<TARGETING::ATTR_FSI_SCOM_MUTEX>();

        if(i_opType == DeviceFW::WRITE)
        {
            memcpy(&(scratchData.data64), io_buffer, 8);

            TRACUCOMP( g_trac_fsiscom, "fsiScomPerformOp> Write(l_scomAddr=0x%X, l_data0=0x%X, l_data1=0x%X)", l_scomAddr, scratchData.data32_0, scratchData.data32_1);


            // atomic section >>
            mutex_lock(l_mutex);
            need_unlock = true;


            //write bits 0-31 to data0
            l_err = DeviceFW::deviceOp( DeviceFW::WRITE,
                                        i_target,
                                        &scratchData.data32_0,
                                        op_size,
                                        DEVICE_FSI_ADDRESS(DATA0_REG));
            if(l_err)
            {
                break;
            }

            //write bits 32-63 to data1
            l_err = DeviceFW::deviceOp( DeviceFW::WRITE,
                                        i_target,
                                        &scratchData.data32_1,
                                        op_size,
                                        DEVICE_FSI_ADDRESS(DATA1_REG));
            if(l_err)
            {
                break;
            }

            //write to FSI2PIB command reg starts write operation
             //bit 0 high => write command
            l_command = 0x80000000 | l_command;
            l_err = DeviceFW::deviceOp( DeviceFW::WRITE,
                                        i_target,
                                        &l_command,
                                        op_size,
                                        DEVICE_FSI_ADDRESS(COMMAND_REG));
            if(l_err)
            {
                break;
            }

            //check status reg to see result
            l_err = DeviceFW::deviceOp( DeviceFW::READ,
                                        i_target,
                                        &l_status,
                                        op_size,
                                        DEVICE_FSI_ADDRESS(STATUS_REG));
            if(l_err)
            {
                break;
            }

            // Check the status reg for errors
            if( (l_status & PIB_ERROR_BITS)      // PCB/PIB Errors
                || (l_status & PIB_ABORT_BIT)  ) // PIB Abort
            {
                TRACFCOMP( g_trac_fsiscom, ERR_MRK"fsiScomPerformOp:Write: PCB/PIB error received: l_status=0x%X)", l_status);
                /*@
                 * @errortype
                 * @moduleid     FSISCOM::MOD_FSISCOM_PERFORMOP
                 * @reasoncode   FSISCOM::RC_WRITE_ERROR
                 * @userdata1    SCOM Addr
                 * @userdata2[00:31]  Target HUID
                 * @userdata2[32:63]  SCOM Status Reg
                 * @devdesc      fsiScomPerformOp> Error returned
                 *               from SCOM Engine after write
                 * @custdesc     A problem occurred during the IPL of the system:
                 *               Error returned from SCOM engine after write.
                 */
                l_err = new ERRORLOG::ErrlEntry(
                                ERRORLOG::ERRL_SEV_UNRECOVERABLE,
                                FSISCOM::MOD_FSISCOM_PERFORMOP,
                                FSISCOM::RC_WRITE_ERROR,
                                l_scomAddr,
                                TWO_UINT32_TO_UINT64(
                                           TARGETING::get_huid(i_target),
                                           l_status));

                // call common error handler to do callouts and recovery
                pib_error_handler( i_target, l_err, l_status, l_scomAddr );

                //Grab the PIB2OPB Status reg for a XSCOM Block error
                if( (l_status & 0x00007000) == 0x00001000 ) //piberr=001
                {
                    //@todo: Switch to external FSI FFDC interfaces RTC:35064
                    TARGETING::Target* l_master = NULL;
                    TARGETING::targetService().
                      masterProcChipTargetHandle(l_master);

                    uint64_t scomdata = 0;
                    size_t scomsize = sizeof(uint64_t);
                    errlHndl_t l_err2 = DeviceFW::deviceOp( DeviceFW::READ,
                                           l_master,
                                           &scomdata,
                                           scomsize,
                                           DEVICE_XSCOM_ADDRESS(0x00020001));
                    if( l_err2 ) {
                        delete l_err2;
                    } else {
                        TRACFCOMP( g_trac_fsiscom, "PIB2OPB Status = %.16X", scomdata );
                    }
                }

                break;
            }

            // atomic section <<
            need_unlock = false;
            mutex_unlock(l_mutex);
        }
        else if(i_opType == DeviceFW::READ)
        {
            TRACUCOMP( g_trac_fsiscom, "fsiScomPerformOp: Read(l_scomAddr=0x%.8X)", l_scomAddr);

            // atomic section >>
            mutex_lock(l_mutex);
            need_unlock = true;


            //write to FSI2PIB command reg starts read operation
            // bit 0 low -> read command
            l_err = DeviceFW::deviceOp( DeviceFW::WRITE,
                                        i_target,
                                        &l_command,
                                        op_size,
                                        DEVICE_FSI_ADDRESS(COMMAND_REG));
            if(l_err)
            {
                break;
            }

            //check ststus reg to see result
            l_err = DeviceFW::deviceOp( DeviceFW::READ,
                                        i_target,
                                        &l_status,
                                        op_size,
                                        DEVICE_FSI_ADDRESS(STATUS_REG));
            if(l_err)
            {
                break;
            }

            // Check the status reg for errors
            if( (l_status & PIB_ERROR_BITS)      // PCB/PIB Errors
                || (l_status & PIB_ABORT_BIT)  ) // PIB Abort
            {
                TRACFCOMP( g_trac_fsiscom, ERR_MRK"fsiScomPerformOp:Read: PCB/PIB error received: l_status=0x%0.8X)", l_status);

                /*@
                 * @errortype
                 * @moduleid     FSISCOM::MOD_FSISCOM_PERFORMOP
                 * @reasoncode   FSISCOM::RC_READ_ERROR
                 * @userdata1    SCOM Addr
                 * @userdata2[00:31]  Target HUID
                 * @userdata2[32:63]  SCOM Status Reg
                 * @devdesc      fsiScomPerformOp> Error returned from SCOM Engine after read.
                 * @custdesc     A problem occurred during the IPL of the system:
                 *               Error returned from SCOM engine after read.
                 */
                l_err = new ERRORLOG::ErrlEntry(ERRORLOG::ERRL_SEV_UNRECOVERABLE,
                                                FSISCOM::MOD_FSISCOM_PERFORMOP,
                                                FSISCOM::RC_READ_ERROR,
                                                l_scomAddr,
                                                TWO_UINT32_TO_UINT64(
                                                 TARGETING::get_huid(i_target),
                                                 l_status));

                // call common error handler to do callouts and recovery
                pib_error_handler( i_target, l_err, l_status, l_scomAddr );

                break;
            }

            //read bits 0-31 to data0
            l_err = DeviceFW::deviceOp( DeviceFW::READ,
                                        i_target,
                                        &scratchData.data32_0,
                                        op_size,
                                        DEVICE_FSI_ADDRESS(DATA0_REG));
            if(l_err)
            {
                break;
            }

            //read bits 32-63 to data1
            l_err = DeviceFW::deviceOp( DeviceFW::READ,
                                        i_target,
                                        &scratchData.data32_1,
                                        op_size,
                                        DEVICE_FSI_ADDRESS(DATA1_REG));
            if(l_err)
            {
                break;
            }

            // atomic section <<
            need_unlock = false;
            mutex_unlock(l_mutex);

            TRACUCOMP( g_trac_fsiscom, "fsiScomPerformOp: Read: l_scomAddr=0x%X, l_data0=0x%X, l_data1=0x%X", l_scomAddr, scratchData.data32_0, scratchData.data32_1);

             memcpy(io_buffer, &(scratchData.data64), 8);
        }
        else
        {
            TRACFCOMP( g_trac_fsiscom, ERR_MRK"fsiScomPerformOp:Unsupported Operation Type: i_opType=%d)", i_opType);

            /*@
             * @errortype
             * @moduleid     FSISCOM::MOD_FSISCOM_PERFORMOP
             * @reasoncode   FSISCOM::RC_INVALID_OPTYPE
             * @userdata1[0:31]    Operation Type (i_opType) : 0=READ, 1=WRITE
             * @userdata1[32:64]   Input scom address
             * @userdata2    Target HUID
             * @devdesc      fsiScomPerformOp> Unsupported Operation Type specified
             * @custdesc     A problem occurred during the IPL of the system:
             *               Unsupported SCOM operation type.
             */
            l_err = new ERRORLOG::ErrlEntry(ERRORLOG::ERRL_SEV_UNRECOVERABLE,
                                            FSISCOM::MOD_FSISCOM_PERFORMOP,
                                            FSISCOM::RC_INVALID_OPTYPE,
                                            TWO_UINT32_TO_UINT64(i_opType,
                                                                 l_scomAddr),
                                            TARGETING::get_huid(i_target),
                                            true /*SW error*/);
            //Add this target to the FFDC
            ERRORLOG::ErrlUserDetailsTarget(i_target,"SCOM Target").
              addToLog(l_err);

            break;

        }

    }while(0);

    if( need_unlock && l_mutex )
    {
        mutex_unlock(l_mutex);
    }


    return l_err;

}