ClRcT clCpmNodeNameGet(ClUint32T argc, ClCharT *argv[], ClCharT **retStr)
{
    ClRcT rc = CL_OK;
    ClNameT nodeName={0};
    *retStr = NULL;
    if(argc > 1 )
    {
        ClCharT tempStr[0x100];
        rc = CL_CPM_RC(CL_ERR_INVALID_PARAMETER);
        snprintf(tempStr, sizeof(tempStr),
                 "Usage: nodename\n");
        *retStr = (ClCharT *) clHeapAllocate(strlen(tempStr) + 1);
        if (*retStr)
            strcpy(*retStr, tempStr);
        goto out;
    }
    rc = clCpmLocalNodeNameGet(&nodeName);
    if(rc != CL_OK)
    {
        rc = CL_CPM_RC(CL_ERR_UNSPECIFIED);
        goto out;
    }
    *retStr = clHeapCalloc(1,nodeName.length+1);
    if(!*retStr)
    {
        rc = CL_CPM_RC(CL_ERR_NO_MEMORY);
        goto out;
    }
    strncpy(*retStr,nodeName.value,nodeName.length);
    rc = CL_OK;

    out:
    return rc;
}
ClRcT clCpmMiddlewareRestartCommand(ClUint32T argc, ClCharT **argv, ClCharT **retStr)
{
    ClRcT rc = CL_CPM_RC(CL_ERR_NO_MEMORY);
    ClIocNodeAddressT nodeAddress = 0;
    ClBoolT graceful = CL_TRUE;
    ClBoolT nodeReset = CL_FALSE;

    *retStr = clHeapAllocate(2*CL_MAX_NAME_LENGTH+1);
    if (!*retStr)
    {
        goto out;
    }

    rc = CL_CPM_RC(CL_ERR_INVALID_PARAMETER);
    if (argc < 2 || argc > 4)
    {
        strncpy(*retStr,
                "Usage : middlewareRestart node-address [graceful] [node-reset]\n"
                "        node-address - Address of the node to be restarted\n"
                "        graceful - value >= 1 indicates graceful restart\n"
                "                 - value 0 indicates ungraceful restart\n"
                "                 default value is 1\n"
                "        node-reset - value >= 1 indicates node is reset\n"
                "                   - value 0 indicates middleware is restarted\n"
                "                 default value is 0\n",
                2*CL_MAX_NAME_LENGTH);
        goto out;
    }

    if(argc >= 2)
        nodeAddress = cpmCliStrToInt(argv[1]);
    
    if(argc >= 3)
        graceful = cpmCliStrToInt(argv[2]) ? CL_TRUE : CL_FALSE;

    if(argc >= 4)
        nodeReset = cpmCliStrToInt(argv[3]) ? CL_TRUE : CL_FALSE;

    rc = clCpmMiddlewareRestart(nodeAddress, graceful, nodeReset);
    if (rc != CL_OK)
    {
        snprintf(*retStr,
                 2*CL_MAX_NAME_LENGTH,
                 "Restarting middleware failed with error [%#x]",
                 rc);
        goto out;
    }

    return CL_OK;
    
    out:
    return rc;
}
ClRcT clCpmRestart(ClUint32T argc, ClCharT **argv, ClCharT **retStr)
{
    ClRcT rc = CL_CPM_RC(CL_ERR_NO_MEMORY);

    *retStr = clHeapAllocate(2*CL_MAX_NAME_LENGTH+1);
    if (!*retStr)
    {
        goto out;
    }

    rc = CL_CPM_RC(CL_ERR_INVALID_PARAMETER);
    if (argc < 2 || argc > 3)
    {
        strncpy(*retStr, 
                "Usage : nodeRestart node-address [graceful]\n"
                "        node-address - Address of the node to be restarted\n"
                "        graceful - value >= 1 indicates graceful restart\n"
                "                 - value 0 indicates ungraceful restart\n"
                "                 default value is 1\n",
                2*CL_MAX_NAME_LENGTH);
    }
    else if (argc == 2)
    {
        rc = clCpmNodeRestart(cpmCliStrToInt(argv[1]), CL_TRUE);
        if (rc != CL_OK)
        {
            snprintf(*retStr,
                     2*CL_MAX_NAME_LENGTH,
                     "Restarting node failed with error [%#x]",
                     rc);
            goto out;
        }
    }
    else if (argc == 3)
    {
        rc = clCpmNodeRestart(cpmCliStrToInt(argv[1]),
                              cpmCliStrToInt(argv[2]) ? CL_TRUE: CL_FALSE);
        if (rc != CL_OK)
        {
            snprintf(*retStr,
                     2*CL_MAX_NAME_LENGTH,
                     "Restarting node failed with error [%#x]",
                     rc);
            goto out;
        }
    }

    return CL_OK;
    
out:
    return rc;
}
ClRcT cpmInvocationAdd(ClUint32T cbType,
                       void *data,
                       ClInvocationT *invocationId,
                       ClUint32T flags)
{
    ClRcT rc = CL_OK;
    ClCpmInvocationT *temp = NULL;
    ClUint32T invocationKey = 0;

    if (cbType < 0x1LL || cbType >= CL_CPM_MAX_CALLBACK || invocationId == NULL)
        CL_CPM_CHECK(CL_LOG_SEV_ERROR, ("Invalid parameter passed \n"),
                     CL_CPM_RC(CL_ERR_INVALID_PARAMETER));

    temp =
            (ClCpmInvocationT *) clHeapAllocate(sizeof(ClCpmInvocationT));
    if (temp == NULL)
        CL_CPM_CHECK(CL_LOG_SEV_ERROR, ("Unable to allocate memory \n"),
                     CL_CPM_RC(CL_ERR_NO_MEMORY));

    clOsalMutexLock(gpClCpm->invocationMutex);

    invocationKey = gpClCpm->invocationKey++;
    CL_CPM_INVOCATION_ID_GET((ClUint64T) cbType, (ClUint64T) invocationKey,
                             *invocationId);

    temp->invocation = *invocationId;
    temp->data = data;
    temp->flags = flags;

    rc = clCntNodeAdd(gpClCpm->invocationTable, (ClCntKeyHandleT)&temp->invocation,
                      (ClCntDataHandleT) temp, NULL);
    if (rc != CL_OK)
    {
        clLogError("NEW", "INVOCATION", "Invocation add for key [%#llx] returned [%#x]", 
                   temp->invocation, rc);
        goto withLock;
    }

    clLogDebug("NEW", "INVOCATION", "Added entry for invocation [%#llx]", temp->invocation);

    clOsalMutexUnlock(gpClCpm->invocationMutex);
    return rc;

  withLock:
    clOsalMutexUnlock(gpClCpm->invocationMutex);
  failure:
    if (temp != NULL)
        clHeapFree(temp);

    return rc;
}
ClRcT clCpmShutDown(ClUint32T argc, ClCharT *argv[], ClCharT **retStr)
{
    ClUint32T rc = CL_OK;

    if (!CL_CPM_IS_ACTIVE())
    {
        cpmCliPrint(retStr,
                    "Node shutdown operation can be performed "
                    "only on CPM/G active");
        rc = CL_CPM_RC(CL_ERR_OP_NOT_PERMITTED);
        goto failure;
    }

    if (2 == argc)
    {
        ClIocNodeAddressT nodeAddress = 0;

        nodeAddress = (ClIocNodeAddressT) cpmCliStrToInt(argv[1]);
        if (nodeAddress <= 0) 
        {
            cpmCliPrint(retStr, "Invalid node address [%s]", argv[1]);
            rc = CL_CPM_RC(CL_ERR_INVALID_PARAMETER);
            goto failure;
        }

        rc = clCpmNodeShutDown(nodeAddress);
        if (CL_OK != rc)
        {
            cpmCliPrint(retStr,
                        "Failed to shutdown the node, error [%#x]",
                        rc);
            goto failure;
        }
    }
    else
    {
        rc = CL_CPM_RC(CL_ERR_INVALID_PARAMETER);
        cpmCliPrint(retStr,
                    "Usage : nodeShutdown <node address>\n"
                    "\tnode address[in decimal] - IOC address "
                    "of the node");
        goto failure;
    }

    return CL_OK;

 failure:
    return rc;
}
ClRcT cpmInvocationGetWithLock(ClInvocationT invocationId,
                               ClUint32T *cbType,
                               void **data)
{
    ClRcT rc = CL_OK;
    ClCntNodeHandleT cntNodeHandle = 0;
    ClCpmInvocationT *invocationData = NULL;

    /*
     * Check the input parameter 
     */
    if ((data == NULL) || (cbType == NULL))
        CL_CPM_CHECK(CL_LOG_SEV_ERROR, ("Invalid parameter passed \n"), CL_CPM_RC(CL_ERR_NULL_POINTER));

    rc = clCntNodeFind(gpClCpm->invocationTable, (ClCntKeyHandleT)&invocationId, &cntNodeHandle);
    if (rc != CL_OK)
        goto failure;

    rc = clCntNodeUserDataGet(gpClCpm->invocationTable, cntNodeHandle, (ClCntDataHandleT *) &invocationData);
    if (rc != CL_OK)
        goto failure;

    *data = invocationData->data;
    CL_CPM_INVOCATION_CB_TYPE_GET(invocationId, *cbType);

    return rc;

  failure:
    return rc;
}
ClRcT cliEOSetState(ClUint32T argc, ClCharT **argv, ClCharT **retStr)
{
    ClRcT rc = CL_OK;
    ClEoIdT eoId;
    ClEoStateT state;
    ClCharT tempStr[256];

    if (argc < THREE_ARGUMENT)
    {
        sprintf(tempStr, "%s%s%s", "Usage: EOStateSet <eoId> <state>\n",
                "\teoId[DEC]: Id assigned to an EO\n",
                "\tState[STRING]: SUSPEND/RESUME\n");
        rc = CL_CPM_RC(CL_ERR_INVALID_PARAMETER);
        goto done;
    }
    else
    {
        eoId = cpmCliStrToInt(argv[1]);
        
        if (0 == strcmp(argv[2], "SUSPEND"))
            state = CL_EO_STATE_SUSPEND;
        else if (0 == strcmp(argv[2], "RESUME"))
            state = CL_EO_STATE_RESUME;
        else
        {
            sprintf(tempStr, "\n Improper state: State: SUSPEND/RESUME\n");
            rc = CL_CPM_RC(CL_ERR_INVALID_PARAMETER);
            goto done;
        }

        rc = clCpmExecutionObjectStateSet(clIocLocalAddressGet(), eoId, state);
        if (rc == CL_OK)
            sprintf(tempStr, "\n State update Successful");
        else
            sprintf(tempStr, "\n State update Failed");
    }

  done:
    *retStr = (ClCharT *) clHeapAllocate(strlen(tempStr) + 1);
    if (*retStr == NULL)
        CL_CPM_CHECK(CL_DEBUG_ERROR, ("\n MAlloc Failed \n"),
                     CL_CPM_RC(CL_ERR_NO_MEMORY));
    strcpy(*retStr, tempStr);

  failure:
    return rc;
}
ClRcT clCpmEventPayLoadExtract(ClEventHandleT eventHandle,
                               ClSizeT eventDataSize,
                               ClCpmEventTypeT cpmEventType,
                               void *payLoad)
{
    ClRcT rc = CL_OK;
    ClBufferHandleT payLoadMsg = 0;
    void *eventData = NULL;

    eventData = clHeapAllocate(eventDataSize);
    if (eventData == NULL)
    {
        clLogWrite(CL_LOG_HANDLE_APP, CL_LOG_SEV_DEBUG, CL_CPM_CLIENT_LIB,
                   CL_LOG_MESSAGE_0_MEMORY_ALLOCATION_FAILED);
        CPM_CLIENT_CHECK(CL_LOG_SEV_ERROR, ("Unable to malloc \n"),
                         CL_CPM_RC(CL_ERR_NO_MEMORY));
    }
    rc = clEventDataGet (eventHandle, eventData,  &eventDataSize);
    if (rc != CL_OK)
    {
        clOsalPrintf("Event Data Get failed. rc=[0x%x]\n", rc);
        goto failure;
    }

    rc = clBufferCreate(&payLoadMsg);
    CL_CPM_CHECK_1(CL_LOG_SEV_ERROR, CL_CPM_LOG_1_BUF_CREATE_ERR, rc, rc,
                   CL_LOG_HANDLE_APP);
    rc = clBufferNBytesWrite(payLoadMsg, (ClUint8T *)eventData,
                             eventDataSize);
    CL_CPM_CHECK_1(CL_LOG_SEV_ERROR, CL_CPM_LOG_1_BUF_WRITE_ERR, rc, rc,
                   CL_LOG_HANDLE_APP);

    switch(cpmEventType)
    {
    case CL_CPM_COMP_EVENT:
        rc = VDECL_VER(clXdrUnmarshallClCpmEventPayLoadT, 4, 0, 0)(payLoadMsg, payLoad);
        CL_CPM_CHECK_0(CL_LOG_SEV_ERROR, CL_LOG_MESSAGE_0_INVALID_BUFFER, rc,
                       CL_LOG_HANDLE_APP);
        break;
    case CL_CPM_NODE_EVENT:
        rc = VDECL_VER(clXdrUnmarshallClCpmEventNodePayLoadT, 4, 0, 0)(payLoadMsg, payLoad);
        CL_CPM_CHECK_0(CL_LOG_SEV_ERROR, CL_LOG_MESSAGE_0_INVALID_BUFFER, rc,
                       CL_LOG_HANDLE_APP);
        break;
    default:
        clOsalPrintf("Invalid event type received.\n");
        goto failure;
        break;
    }

failure:
    clBufferDelete(&payLoadMsg);
    clHeapFree(eventData);
    return rc;
}
ClRcT clCpmLogFileRotate(ClUint32T argc, ClCharT **argv, ClCharT **retStr)
{
    ClRcT rc = CL_CPM_RC(CL_ERR_NO_MEMORY);

    *retStr = clHeapAllocate(50+1);
    if(!*retStr)
    {
        goto out;
    }
    rc = CL_CPM_RC(CL_ERR_INVALID_PARAMETER);
    if(argc != 1)
    {
        strncpy(*retStr,"Usage: logrotate\n",50);
        goto out;
    }
    cpmLoggerRotateEnable();
    rc = CL_OK;
    out:
    return rc;
}
ClRcT cpmNodeFindLocked(SaUint8T *name, ClCpmLT **cpmL)
{
    ClUint16T nodeKey = 0;
    ClCntNodeHandleT hNode = 0;
    ClCpmLT *tempNode = NULL;
    ClUint32T rc = CL_OK, numNode=0;

    rc = clCksm16bitCompute((ClUint8T *) name, strlen((const ClCharT*)name), &nodeKey);
    CL_CPM_CHECK_2(CL_LOG_SEV_ERROR, CL_CPM_LOG_2_CNT_CKSM_ERR, name, rc, rc,
                   CL_LOG_HANDLE_APP);

    rc = clCntNodeFind(gpClCpm->cpmTable, (ClPtrT)(ClWordT)nodeKey, &hNode);
    CL_CPM_CHECK_3(CL_LOG_SEV_ERROR, CL_CPM_LOG_3_CNT_ENTITY_SEARCH_ERR, "node",
                   name, rc, rc, CL_LOG_HANDLE_APP);

    rc = clCntKeySizeGet(gpClCpm->cpmTable, (ClPtrT)(ClWordT)nodeKey,
                         &numNode);
    CL_CPM_CHECK_1(CL_LOG_SEV_ERROR, CL_CPM_LOG_1_CNT_KEY_SIZE_GET_ERR, rc, rc,
                   CL_LOG_HANDLE_APP);

    while (numNode > 0)
    {
        rc = clCntNodeUserDataGet(gpClCpm->cpmTable, hNode,
                                  (ClCntDataHandleT *) &tempNode);
        CL_CPM_CHECK_1(CL_LOG_SEV_ERROR, CL_CPM_LOG_1_CNT_NODE_USR_DATA_GET_ERR,
                       rc, rc, CL_LOG_HANDLE_APP);
        if (!strcmp(tempNode->nodeName, (const ClCharT*)name))
        {
            *cpmL = tempNode;
            goto done;
        }
        if(--numNode)
        {
            rc = clCntNextNodeGet(gpClCpm->cpmTable,hNode,&hNode);
            if(rc != CL_OK)
            {
                break;
            }
        }
    }

    rc = CL_CPM_RC(CL_ERR_DOESNT_EXIST);
    CL_CPM_CHECK_3(CL_LOG_SEV_ERROR, CL_CPM_LOG_3_CNT_ENTITY_SEARCH_ERR,
                   "node", name, rc, rc, CL_LOG_HANDLE_APP);

done:
    return CL_OK;

failure:
    return rc;
}
ClRcT clCpmNodeErrorReport(ClUint32T argc, ClCharT *argv[], ClCharT **retStr)
{
    ClUint32T rc = CL_OK;
    if (2 == argc)
    {
        ClIocNodeAddressT nodeAddress = 0;
        nodeAddress = (ClIocNodeAddressT) cpmCliStrToInt(argv[1]);
        if (nodeAddress <= 0) 
        {
            cpmCliPrint(retStr, "Invalid node address [%s]", argv[1]);
            rc = CL_CPM_RC(CL_ERR_INVALID_PARAMETER);
            goto failure;
        }

        rc = nodeErrorAssert(nodeAddress, CL_TRUE);
        if (CL_OK != rc)
        {
            cpmCliPrint(retStr,
                        "Node error report failed, error [%#x]",
                        rc);
            goto failure;
        }
    }
    else
    {
        rc = CL_CPM_RC(CL_ERR_INVALID_PARAMETER);
        cpmCliPrint(retStr,
                    "Usage : nodeErrorReport <node address>\n"
                    "\tnode address[in decimal] - IOC address "
                    "of the node");
        goto failure;
    }

    return CL_OK;

 failure:
    return rc;
}
ClRcT clCpmClusterListAll(ClUint32T argc, ClCharT *argv[], ClCharT **retStr)
{
    ClRcT rc = CL_OK;

    if (gpClCpm->pCpmConfig->cpmType == CL_CPM_GLOBAL)
        rc = _cpmClusterConfigList(argc, retStr);
    else
    {
        CL_DEBUG_PRINT(CL_DEBUG_ERROR,
                       ("CPM Local Doesn't contain the cluster wide configuration \n"));
        rc = CL_CPM_RC(CL_ERR_BAD_OPERATION);
    }

    return rc;
}
ClRcT clCpmHeartbeat(ClUint32T argc, ClCharT **argv, ClCharT **retStr)
{
    ClRcT rc = CL_CPM_RC(CL_ERR_NO_MEMORY);

    *retStr = clHeapCalloc(sizeof(**retStr), 51);
    if(!*retStr)
    {
        goto out;
    }
    rc = CL_CPM_RC(CL_ERR_INVALID_PARAMETER);
    if(argc != 2)
    {
        strncpy(*retStr,"Usage: heartbeat [enable | disable | status]\n",50);
        goto out;
    }
    if(!strcasecmp(argv[1],"enable"))
    {
        clIocHeartBeatUnpause();
    }
    else if(!strcasecmp(argv[1],"disable"))
    {
        clIocHeartBeatPause();
    }
    else if(!strcasecmp(argv[1],"status"))
    {
        strncpy(*retStr, clIocHeartBeatStatusGet(), 50);
    }
    else
    {
        strncpy(*retStr,"Usage: heartbeat [enable | disable]\n", 50);
        goto out;
    }
    rc = CL_OK;
    out:
    return rc;
}
ClUint32T cpmNodeFindByNodeId(ClUint32T nodeId, ClCpmLT **cpmL)
{
    ClRcT rc = CL_OK;
    ClCntNodeHandleT cpmNode = 0;
    ClUint32T cpmLCount = 0;
    ClCpmLT *tempCpmL = NULL;
    ClUint32T found = 0;

    cpmLCount = gpClCpm->noOfCpm;
    if (gpClCpm->pCpmConfig->cpmType == CL_CPM_GLOBAL && cpmLCount != 0)
    {
        rc = clCntFirstNodeGet(gpClCpm->cpmTable, &cpmNode);
        CL_CPM_CHECK_2(CL_LOG_SEV_ERROR, CL_CPM_LOG_2_CNT_FIRST_NODE_GET_ERR, "CPM-L", rc, rc, CL_LOG_HANDLE_APP);

        while (cpmLCount)
        {
            rc = clCntNodeUserDataGet(gpClCpm->cpmTable, cpmNode, (ClCntDataHandleT *) &tempCpmL);
            CL_CPM_CHECK_1(CL_LOG_SEV_ERROR, CL_CPM_LOG_1_CNT_NODE_USR_DATA_GET_ERR, rc, rc, CL_LOG_HANDLE_APP);

            if (tempCpmL->pCpmLocalInfo)
            {
                if ((ClUint32T) tempCpmL->pCpmLocalInfo->nodeId == nodeId)
                {
                    *cpmL = tempCpmL;
                    found = 1;
                    break;
                }
            }
            cpmLCount--;

            if (cpmLCount)
            {
                rc = clCntNextNodeGet(gpClCpm->cpmTable, cpmNode, &cpmNode);
                CL_CPM_CHECK_2(CL_LOG_SEV_ERROR, CL_CPM_LOG_2_CNT_NEXT_NODE_GET_ERR, "CPM-L", rc, rc, CL_LOG_HANDLE_APP);
            }
        }
    }
    if(found == 1)
        return CL_OK;
    else
        return CL_CPM_RC(CL_ERR_DOESNT_EXIST);

  failure:
    *cpmL = NULL;
    return rc;
}
static void cpmCliPrint(ClCharT **retStr, const ClCharT *fmt, ...)
{
    va_list args;
    ClCharT tempStr[CL_MAX_NAME_LENGTH] = {0};

    va_start(args, fmt);
    vsnprintf(tempStr, CL_MAX_NAME_LENGTH-1, fmt, args);
    va_end(args);

    *retStr = (ClCharT *) clHeapAllocate(strlen(tempStr) + 1);
    if (!*retStr) 
    {
        clLogError(CPM_LOG_AREA_CPM, CPM_LOG_CTX_CPM_CLI,
                   "Failed to allocate memory, error [%#x]",
                   CL_CPM_RC(CL_ERR_NULL_POINTER));
        return;
    }
    strcpy(*retStr, tempStr);
}
ClRcT _clCpmComponentListAll(ClInt32T argc, ClCharT **retStr)
{
    ClCntNodeHandleT hNode = 0;
    ClCpmComponentT *comp = NULL;
    ClUint32T rc = CL_OK, count;
    ClCpmEOListNodeT *eoList = NULL;
    ClCharT state[10] = "\0";
    ClCharT status[10] = "\0";
    ClCharT tempStr[256];
    ClCharT *tmpStr = NULL;
    ClBufferHandleT message;
    ClCharT cpmCompName[CL_MAX_NAME_LENGTH] = {0};
    
    rc = clBufferCreate(&message);
    CL_CPM_CHECK(CL_DEBUG_ERROR, ("Unable to create message %x\n", rc), rc);

    if (argc != ONE_ARGUMENT)
    {
        rc = clBufferNBytesWrite(message, (ClUint8T *) STR_AND_SIZE("Usage: compList"));
        CL_CPM_CHECK(CL_DEBUG_ERROR, ("Unable to write message %x\n", rc), rc);
        rc = CL_CPM_RC(CL_ERR_INVALID_PARAMETER);
        goto done;
    }

    count = gpClCpm->noOfComponent;
    snprintf(cpmCompName,
             CL_MAX_NAME_LENGTH-1,
             "%s_%s",
             CL_CPM_COMPONENT_NAME,
             gpClCpm->pCpmLocalInfo->nodeName);

    rc = clCntFirstNodeGet(gpClCpm->compTable, &hNode);
    CL_CPM_CHECK(CL_DEBUG_ERROR, ("\n Unable to Get First component \n"), rc);

    rc = clBufferNBytesWrite(message, (ClUint8T *) STR_AND_SIZE("################### List Of Components ########################\n"));
    CL_CPM_CHECK(CL_DEBUG_ERROR, ("\n Unable to write message \n"), rc);

    rc = clCntNodeUserDataGet(gpClCpm->compTable, hNode,(ClCntDataHandleT *) &comp);
    CL_CPM_CHECK(CL_DEBUG_ERROR, ("\n Unable to Get Node  Data \n"), rc);

    rc = clBufferNBytesWrite(message, STR_AND_SIZE("        CompName              | compId  |  eoPort  |   PID   | RestartCount  | PresenceState\n"));
    CL_CPM_CHECK(CL_DEBUG_ERROR, ("\n Unable to write message \n"), rc);

    rc = clBufferNBytesWrite(message, STR_AND_SIZE("\t\t     ID |     Port |     Name  |    Health |Recv Threads \n"));   
    CL_CPM_CHECK(CL_DEBUG_ERROR, ("\n Unable to write message \n"), rc);

    rc = clBufferNBytesWrite(message, STR_AND_SIZE("========================================================================================\n"));    
    CL_CPM_CHECK(CL_DEBUG_ERROR, ("\n Unable to write message \n"), rc);

    while (count)
    {
        
        if (strcmp(comp->compConfig->compName, cpmCompName)!=0)  /* Skip if it is the CPM component */
        {
            
            eoList = comp->eoHandle;

            int len = sprintf(tempStr, "%30s| 0x%x | 0x%x |%8d |%14d |%15s\n",
                              comp->compConfig->compName, comp->compId,
                              comp->eoPort, comp->processId, comp->compRestartCount,
                              _cpmPresenceStateNameGet(comp->compPresenceState));
            
            if (comp->compConfig->compProperty != CL_AMS_COMP_PROPERTY_SA_AWARE)
            {

                if(!eoList || !eoList->eoptr)
                {
                    len += snprintf(tempStr + len, sizeof(tempStr) - len, 
                                    "\t\t   0x%x  |  0x%x   |%10s |%10s |%04d \n",
                                    0, 0, "-", "-", 0);
                }
            }

            rc = clBufferNBytesWrite(message, (ClUint8T *) tempStr,len);
            CL_CPM_CHECK(CL_DEBUG_ERROR, ("\n Unable to write message \n"), rc);

            while (eoList != NULL && eoList->eoptr != NULL)
            {
                compMgrStateStatusGet(eoList->status, eoList->eoptr->state, status, sizeof(status),
                                      state, sizeof(state));
                int noOfThreads = (eoList->eoptr->appType == CL_EO_USE_THREAD_FOR_RECV) ? eoList->eoptr->noOfThreads + 1: eoList->eoptr->noOfThreads;

                int len = sprintf(tempStr, "\t\t   0x%llx  |  0x%x   |%10s |%10s |%04d \n",
                                  eoList->eoptr->eoID, eoList->eoptr->eoPort,
                                  eoList->eoptr->name, status,
                                  noOfThreads);
                rc = clBufferNBytesWrite(message, (ClUint8T *) tempStr, len);
                CL_CPM_CHECK(CL_DEBUG_ERROR, ("\n Unable to write message \n"), rc);
                eoList = eoList->pNext;
            }
        
            rc = clBufferNBytesWrite(message, STR_AND_SIZE("-----------------------------------------------------------------------------------------\n"));
            CL_CPM_CHECK(CL_DEBUG_ERROR, ("\n Unable to write message \n"), rc);
        
        }
        
        count--;
        if (count)
        {
            rc = clCntNextNodeGet(gpClCpm->compTable, hNode, &hNode);
            CL_CPM_CHECK(CL_DEBUG_ERROR, ("Unable to Get Node  Data %x\n", rc), rc);

            rc = clCntNodeUserDataGet(gpClCpm->compTable, hNode, (ClCntDataHandleT *) &comp);
            CL_CPM_CHECK(CL_DEBUG_ERROR, ("Unable to Get Node user Data %x\n", rc), rc);
        }

    }

    /*
     * Bug 4986 :
     * Moved the code to NULL terminate the string
     * below the done: label, so that the usage string
     * written to the buffer is also NULL terminated.
     */
done:
    /*
     * NULL terminate the string 
     */
    rc = clBufferNBytesWrite(message, (ClUint8T *) "\0", 1);
    CL_CPM_CHECK(CL_DEBUG_ERROR, ("\n Unable to write message \n"), rc);

    rc = clBufferFlatten(message, (ClUint8T **) &tmpStr);
    CL_CPM_CHECK(CL_DEBUG_ERROR, ("Unable to flatten the message \n"), rc);

    *retStr = tmpStr;
    
    clBufferDelete(&message);
    return rc;

failure:
    clBufferDelete(&message);
    return rc;
}
ClRcT cpmInvocationClearCompInvocation(SaNameT *compName)
{
    ClRcT rc = CL_OK;
    ClCntNodeHandleT nodeHandle, nextNodeHandle;
    ClCpmInvocationT *invocationData = NULL;
    void *data = NULL;

    /*
     * Check the input parameter 
     */
    if (!compName)
    {
        CL_CPM_CHECK(CL_LOG_SEV_ERROR, ("Invalid parameter passed \n"),
                     CL_CPM_RC(CL_ERR_NULL_POINTER));
    }

    clOsalMutexLock(gpClCpm->invocationMutex);

    rc = clCntFirstNodeGet(gpClCpm->invocationTable, &nodeHandle);
    if (rc != CL_OK)
        goto withLock;


    while (nodeHandle)
    {

        rc = clCntNodeUserDataGet(gpClCpm->invocationTable, nodeHandle,
                                  (ClCntDataHandleT *) &invocationData);

        if (rc != CL_OK)
            goto withLock;

        rc = clCntNextNodeGet(gpClCpm->invocationTable, nodeHandle,
                              &nextNodeHandle);

        if((data = invocationData->data))
        {
            ClUint32T matched = 0;
            if ((invocationData->flags & CL_CPM_INVOCATION_AMS))
            {
                matched = !strncmp((const ClCharT *) (((ClAmsInvocationT*) data)->compName.value), (const ClCharT *) compName->value,
                                ((ClAmsInvocationT*) data)->compName.length);
            }
            else if ((invocationData->flags & CL_CPM_INVOCATION_CPM))
            {
                matched = !strncmp((const ClCharT *) (((ClCpmComponentT*) data)->compConfig->compName), (const ClCharT *) compName->value,
                                compName->length);
            }
            
            if(matched)
            {
                clLogDebug("INVOCATION", "CLEAR", "Clearing invocation for component [%.*s] "
                           "invocation [%#llx]", compName->length, compName->value, invocationData->invocation);
                if (clCntNodeDelete(gpClCpm->invocationTable, nodeHandle) != CL_OK)
                    goto withLock;
                if( (invocationData->flags & CL_CPM_INVOCATION_DATA_COPIED) )
                    clHeapFree(data);
                clHeapFree(invocationData);
            }
        }
        if (CL_GET_ERROR_CODE(rc) == CL_ERR_NOT_EXIST)
            break;

        if (rc != CL_OK)
            goto withLock;

        nodeHandle = nextNodeHandle;

    }

    clOsalMutexUnlock(gpClCpm->invocationMutex);
    return CL_OK;

    withLock:
    failure:
    clOsalMutexUnlock(gpClCpm->invocationMutex);
    return rc;
}
static ClRcT cpmComponentAdd(ClCharT *compName)
{
    ClRcT rc = CL_CPM_RC(CL_ERR_NULL_POINTER);
    ClCpmCompConfigT compConfig = 
    {
        "",
        CL_FALSE,
        CL_AMS_COMP_PROPERTY_SA_AWARE,
        CL_CPM_COMP_SINGLE_PROCESS,
        "invalid",
        {(ClCharT*) "invalid", NULL},
        {NULL},
        "",
        "",
        0,
        0,
        0,
        0,
        0,
        {
            CL_CPM_COMPONENT_DEFAULT_HC_TIMEOUT,
            2 * CL_CPM_COMPONENT_DEFAULT_HC_TIMEOUT,
            CL_AMS_RECOVERY_NO_RECOMMENDATION
        }
    };
    ClCpmComponentT *comp = NULL;
    ClUint16T compKey = 0;
    const ClCharT *config = NULL;
    ClCharT cleanupCMD[CL_MAX_NAME_LENGTH];
        
    if (!compName)
    {
        clLogError(CPM_LOG_AREA_CPM, CPM_LOG_CTX_CPM_MGM,
                   "NULL pointer passed.");
        goto failure;
    }

    cleanupCMD[0] = 0;
    if( (config = getenv("ASP_CONFIG")) )
    {
        snprintf(cleanupCMD, sizeof(cleanupCMD), "%s/%s", config, CL_CPM_COMP_CLEANUP_SCRIPT);
        if(access(cleanupCMD, R_OK | X_OK))
            cleanupCMD[0] = 0;
    }
    rc = cpmCompFind((SaUint8T *)compName, gpClCpm->compTable, &comp);
    if (comp)
    {
        clLogWarning(CPM_LOG_AREA_CPM, CPM_LOG_CTX_CPM_MGM,
                     "Component [%s] already exists on this node",
                     compName);
        rc = CL_CPM_RC(CL_ERR_ALREADY_EXIST);
        goto failure;
    }

    strncpy(compConfig.compName, compName, CL_MAX_NAME_LENGTH-1);
    if(cleanupCMD[0])
        strncpy(compConfig.cleanupCMD, cleanupCMD, sizeof(compConfig.cleanupCMD)-1);

    rc = cpmCompConfigure(&compConfig, &comp);
    if (CL_OK != rc)
    {
        clLogError(CPM_LOG_AREA_CPM, CPM_LOG_CTX_CPM_MGM,
                   "Failed to configure component, error [%#x]",
                   rc);
        goto failure;
    }

    rc = clCksm16bitCompute((ClUint8T *) comp->compConfig->compName,
                            strlen(comp->compConfig->compName),
                            &compKey);
    if (CL_OK != rc)
    {
        clLogError(CPM_LOG_AREA_CPM, CPM_LOG_CTX_CPM_MGM,
                   "Failed to compute checksum for component, "
                   "error [%#x]",
                   rc);
        goto failure;
    }

    clOsalMutexLock(gpClCpm->compTableMutex);
    rc = clCntNodeAdd(gpClCpm->compTable,
                      (ClCntKeyHandleT)(ClWordT)compKey,
                      (ClCntDataHandleT) comp,
                      NULL);
    if (CL_OK != rc)
    {
        clLogError(CPM_LOG_AREA_CPM, CPM_LOG_CTX_CPM_MGM,
                   "Failed to add node to the CPM component table, "
                   "error [%#x]",
                   rc);
        clOsalMutexUnlock(gpClCpm->compTableMutex);
        goto failure;
    }
    ++gpClCpm->noOfComponent;
    clOsalMutexUnlock(gpClCpm->compTableMutex);

    return CL_OK;

failure:
    return rc;
}
static ClRcT cpmNodeRmv(ClCharT *nodeName)
{
    ClRcT rc = CL_OK;
    ClUint16T nodeKey = 0;
    ClCntNodeHandleT hNode = 0;
    ClUint32T numNode = 0;
    ClCpmLT *cpm = NULL;
    ClBoolT done = CL_NO;
    if (!nodeName)
    {
        clLogError(CPM_LOG_AREA_CPM, CPM_LOG_CTX_CPM_MGM,
                   "NULL pointer passed.");
        goto failure;
    }

    rc = clCksm16bitCompute((ClUint8T *)nodeName,
                            strlen(nodeName),
                            &nodeKey);
    if (CL_OK != rc)
    {
        clLogError(CPM_LOG_AREA_CPM, CPM_LOG_CTX_CPM_MGM,
                   "Failed to compute checksum for node, "
                   "error [%#x]",
                   rc);
        goto failure;
    }

    clOsalMutexLock(gpClCpm->cpmTableMutex);

    rc = clCntNodeFind(gpClCpm->cpmTable,
                       (ClCntKeyHandleT)(ClWordT)nodeKey,
                       &hNode);
    if (CL_OK != rc)
    {
        clLogError(CPM_LOG_AREA_CPM, CPM_LOG_CTX_CPM_MGM,
                   "Failed to find node [%s], error [%#x]",
                   nodeName,
                   rc);
        goto unlock;
    }

    rc = clCntKeySizeGet(gpClCpm->cpmTable,
                         (ClCntKeyHandleT)(ClWordT)nodeKey,
                         &numNode);
    if (CL_OK != rc)
    {
        clLogError(CPM_LOG_AREA_CPM, CPM_LOG_CTX_CPM_MGM,
                   "Unable to get key size, error [%#x]",
                   rc);
        goto unlock;
    }

    while (numNode > 0)
    {
        rc = clCntNodeUserDataGet(gpClCpm->cpmTable,
                                  hNode,
                                  (ClCntNodeHandleT *) &cpm);
        if (CL_OK != rc)
        {
            clLogError(CPM_LOG_AREA_CPM, CPM_LOG_CTX_CPM_MGM,
                       "Unable to get user data, error [%#x]",
                       rc);
            goto unlock;
        }

        if (!strncmp(nodeName, cpm->nodeName, CL_MAX_NAME_LENGTH-1))
        {
            clCntNodeDelete(gpClCpm->cpmTable, hNode);
            done = CL_YES;
            break;
        }

        if (--numNode)
        {
            rc = clCntNextNodeGet(gpClCpm->cpmTable, hNode, &hNode);
            if (CL_OK != rc)
            {
                break;
            }
        }
    }

    if (!done)
    {
        rc = CL_CPM_RC(CL_ERR_DOESNT_EXIST);
        goto unlock;
    }

    --gpClCpm->noOfCpm;

    clOsalMutexUnlock(gpClCpm->cpmTableMutex);

    /*
     * Delete from slot table
     */
    clOsalMutexLock(&gpClCpm->cpmMutex);
    if(cpmSlotClassDelete(nodeName) != CL_OK)
    {
        clLogWarning("CPM", "MGMT", "Slot class delete failed for node [%s]", nodeName);
    }
    clOsalMutexUnlock(&gpClCpm->cpmMutex);

    return CL_OK;

unlock:
    clOsalMutexUnlock(gpClCpm->cpmTableMutex);
failure:
    return rc;
}
SaAisErrorT clClovisToSafError(ClRcT clError)
{
    SaAisErrorT safError = SA_AIS_ERR_LIBRARY;

    /* First check component specific error translations */
    switch(clError)
    {
        case CL_CPM_RC(CL_CPM_ERR_OPERATION_IN_PROGRESS):
            safError = SA_AIS_ERR_BUSY;
            break;
    }

    if (safError != SA_AIS_ERR_LIBRARY) return safError;
    
    /* Next check to see if the error can be translated generically */    
    switch(CL_GET_ERROR_CODE(clError))
    {
        case CL_OK:
        {
            safError = SA_AIS_OK;
            break;
        }
        case CL_ERR_VERSION_MISMATCH:
        {
            safError = SA_AIS_ERR_VERSION;
            break;
        }
        case CL_ERR_TIMEOUT:
        {
            safError = SA_AIS_ERR_TIMEOUT;
            break;
        }
        case CL_ERR_TRY_AGAIN:
        {
            safError = SA_AIS_ERR_TRY_AGAIN;
            break;
        }
        case CL_ERR_INVALID_PARAMETER:
        {
            safError = SA_AIS_ERR_INVALID_PARAM;
            break;
        }
        case CL_ERR_NO_MEMORY:
        {
            safError = SA_AIS_ERR_NO_MEMORY;
            break;
        }
        case CL_ERR_INVALID_HANDLE:
        {
            safError = SA_AIS_ERR_BAD_HANDLE;
            break;
        }
        case CL_ERR_OP_NOT_PERMITTED:
        {
            safError = SA_AIS_ERR_ACCESS;
            break;
        }
        case CL_ERR_DOESNT_EXIST:
        {
            safError = SA_AIS_ERR_NOT_EXIST;
            break;
        }
        case CL_ERR_ALREADY_EXIST:
        {
            safError = SA_AIS_ERR_EXIST;
            break;
        }
        case CL_ERR_NO_SPACE:
        {
            safError = SA_AIS_ERR_NO_SPACE;
            break;
        }
        case CL_ERR_NO_RESOURCE:
        {
            safError = SA_AIS_ERR_NO_RESOURCES;
            break;
        }
        case CL_ERR_NOT_IMPLEMENTED:
        {
            safError = SA_AIS_ERR_NOT_SUPPORTED;
            break;
        }
        case CL_ERR_BAD_OPERATION:
        {
            safError = SA_AIS_ERR_BAD_OPERATION;
            break;
        }
        case CL_ERR_BAD_FLAG:
        {
            safError = SA_AIS_ERR_BAD_FLAGS;
            break;
        }
        case CL_ERR_NULL_POINTER:
        {
            safError = SA_AIS_ERR_INVALID_PARAM;
            break;
        }
        default:
        {
            clLogWarning("AMF", "SAF",
                         "Clovis error code [%#x] is not mapped to a valid "
                         "SAF error code, returning default [%#x]",
                         CL_GET_ERROR_CODE(clError),
                         (ClUint32T)safError);
            break;
        }
    }

    return safError;
}
static void cpmMakeSCActiveOrDeputy(const ClGmsClusterNotificationBufferT *notificationBuffer,
                                    ClCpmLocalInfoT *pCpmLocalInfo)
{
    ClUint32T rc = CL_OK;
    ClGmsNodeIdT prevMasterNodeId = gpClCpm->activeMasterNodeId;
    ClBoolT leadershipChanged = notificationBuffer->leadershipChanged;
    
    /*  
     * Check for initial leadership state incase the cluster track from AMF was issued
     * after GMS leader election was done and GMS responded back with a track with a leadership changed
     * set to FALSE for a CURRENT async request from AMF.
     */
    if(leadershipChanged == CL_FALSE && 
       (ClInt32T) notificationBuffer->leader == pCpmLocalInfo->nodeId &&
       (ClInt32T) prevMasterNodeId != pCpmLocalInfo->nodeId && 
       gpClCpm->haState == CL_AMS_HA_STATE_NONE)
        leadershipChanged = CL_TRUE;
        
    if (leadershipChanged == CL_TRUE)
    {
        if ( (ClInt32T) notificationBuffer->leader == pCpmLocalInfo->nodeId)
        {
            clLogInfo(CPM_LOG_AREA_CPM, CPM_LOG_CTX_CPM_GMS,
                      "Node [%d] has become the leader of the cluster",
                      pCpmLocalInfo->nodeId);

            if(gpClCpm->haState != CL_AMS_HA_STATE_ACTIVE)
            {
                rc = cpmUpdateTL(CL_AMS_HA_STATE_ACTIVE);
                if (rc != CL_OK)
                {
                    clLogWrite(CL_LOG_HANDLE_APP, CL_LOG_SEV_DEBUG, NULL,
                               CL_CPM_LOG_1_TL_UPDATE_FAILURE, rc);
                }
            }
            gpClCpm->deputyNodeId = notificationBuffer->deputy;
        }
        else if ((ClInt32T) notificationBuffer->deputy == pCpmLocalInfo->nodeId)
        {
            clLogInfo(CPM_LOG_AREA_CPM, CPM_LOG_CTX_CPM_GMS,
                      "Node [%d] has become the deputy of the cluster",
                      pCpmLocalInfo->nodeId);
            /*
             * Deregister the active registration if going from active to standby.
             */
            if(gpClCpm->haState == CL_AMS_HA_STATE_ACTIVE)
            {
                clIocTransparencyDeregister(pCpmLocalInfo->nodeId << CL_CPM_IOC_SLOT_BITS);
            }
            rc = cpmUpdateTL(CL_AMS_HA_STATE_STANDBY);
            if (rc != CL_OK)
            {
                clLogWrite(CL_LOG_HANDLE_APP, CL_LOG_SEV_DEBUG, NULL,
                           CL_CPM_LOG_1_TL_UPDATE_FAILURE, rc);
            }
        }

        if ((gpClCpm->haState == CL_AMS_HA_STATE_ACTIVE) && 
            ( (ClInt32T) notificationBuffer->leader != pCpmLocalInfo->nodeId))
        {
            clLogDebug(CPM_LOG_AREA_CPM, CPM_LOG_CTX_CPM_GMS,
                       "Node [%d] is changing HA state from active to standby",
                       pCpmLocalInfo->nodeId);
              
            /*
             * Deregister the entry during a state change.
             */
            if ( (ClInt32T) notificationBuffer->deputy != pCpmLocalInfo->nodeId)
            {
                clIocTransparencyDeregister((pCpmLocalInfo->nodeId) << CL_CPM_IOC_SLOT_BITS);
            }

            /*
             * Inform AMS to become standby and read the checkpoint.
             */
            if ((gpClCpm->cpmToAmsCallback != NULL) && 
                (gpClCpm->cpmToAmsCallback->amsStateChange != NULL))
            {
                clLogDebug(CPM_LOG_AREA_CPM, CPM_LOG_CTX_CPM_GMS,
                           "Informing AMS on node [%d] to change state "
                           "from active to standby...",
                           pCpmLocalInfo->nodeId);

                rc = gpClCpm->cpmToAmsCallback->amsStateChange(CL_AMS_STATE_CHANGE_ACTIVE_TO_STANDBY |
                                                               CL_AMS_STATE_CHANGE_USE_CHECKPOINT);
                if (CL_OK != rc)
                {
                    clLogWarning(CPM_LOG_AREA_CPM, CPM_LOG_CTX_CPM_AMS,
                                 "AMS state change from active to standby "
                                 "returned [%#x]",
                                 rc);
                }

                cpmWriteNodeStatToFile("AMS", CL_NO);

                if(!gClAmsSwitchoverInline)
                {
                    if (((notificationBuffer->numberOfItems == 0) &&
                         (notificationBuffer->notification == NULL)) &&
                        gpClCpm->polling &&
                        (gpClCpm->nodeLeaving == CL_FALSE))
                    {
                        /*
                         * This indicates that leader election API of
                         * GMS was called.  Since this involves
                         * interaction among only system controllers,
                         * we don't need to restart the worker nodes
                         * like in the case of split brain handling.
                         */
                        
                        cpmActive2Standby(CL_NO);
                    }
                    else if (( (ClInt32T) notificationBuffer->deputy == pCpmLocalInfo->nodeId) && gpClCpm->polling && (gpClCpm->nodeLeaving == CL_FALSE))
                    {
                        /*
                         * We try and handle a possible split brain
                         * since presently GMS shouldnt be reelecting.
                         * And even if it does, its pretty much
                         * invalid with respect to AMS where you could
                         * land up with 2 actives.
                         */
                     
                        /*
                         * We arent expected to return back.
                         */
                        cpmActive2Standby(CL_NO);
                    }
                }
            }

            /*
             * Bug 4168:
             * Updating the data structure gpClCpm, when the active becomes
             * standby.
             */
            gpClCpm->haState = CL_AMS_HA_STATE_STANDBY;
            gpClCpm->activeMasterNodeId = notificationBuffer->leader;
            gpClCpm->deputyNodeId = notificationBuffer->deputy;
            if(gClAmsSwitchoverInline)
            {
                /*
                 *Re-register with active.
                 */
                clOsalMutexUnlock(&gpClCpm->clusterMutex);
                cpmSwitchoverActive();
                clOsalMutexLock(&gpClCpm->clusterMutex);
            }
        }
        else if ((gpClCpm->haState == CL_AMS_HA_STATE_STANDBY) && 
                 ( (ClInt32T) notificationBuffer->leader == pCpmLocalInfo->nodeId))
        {
            rc = cpmStandby2Active(prevMasterNodeId, 
                                   notificationBuffer->deputy);
            if (CL_OK != rc)
            {
                return;
            }
        }
        else if ((gpClCpm->haState == CL_AMS_HA_STATE_NONE) && 
                 ( (ClInt32T) notificationBuffer->leader ==
                  pCpmLocalInfo->nodeId))
        {
            /*
             * Bug 4411:
             * Added the if-else block.
             * Calling the AMS initialize only if both the callback pointers
             * are not NULL.
             * FIXME: This change is sort of workaround for 2.2.
             * Neat solution is to protect gpClCpm structure and fields properly
             */
            if ((gpClCpm->amsToCpmCallback != NULL) &&
                (gpClCpm->cpmToAmsCallback != NULL))
            {
                clLogDebug(CPM_LOG_AREA_CPM, CPM_LOG_CTX_CPM_AMS,"Starting AMS in active mode...");

                rc = clAmsStart(&gAms,CL_AMS_INSTANTIATE_MODE_ACTIVE | CL_AMS_INSTANTIATE_USE_CHECKPOINT);
                /*
                 * Bug 4092:
                 * If the AMS intitialize fails then do the 
                 * self shut down.
                 */
                if (CL_OK != rc)
                {
                    clLogCritical(CPM_LOG_AREA_CPM, CPM_LOG_CTX_CPM_AMS,"Unable to initialize AMF, error = [%#x]", rc);

                    gpClCpm->amsToCpmCallback = NULL;
                    cpmReset(NULL,NULL);
                    return;
                }
            }
            else
            {
                rc = CL_CPM_RC(CL_ERR_NULL_POINTER);
                 
                if (!gpClCpm->polling)
                {
                    clLogCritical(CPM_LOG_AREA_CPM, CPM_LOG_CTX_CPM_AMS, "AMF finalize called before AMF initialize during node shutdown.");
                }
                else
                {
                    clLogCritical(CPM_LOG_AREA_CPM, CPM_LOG_CTX_CPM_AMS, "Unable to initialize AMF, error = [%#x]", rc);
                     
                    cpmRestart(NULL,NULL);
                }
                return;
            }
             
            gpClCpm->haState = CL_AMS_HA_STATE_ACTIVE;
            gpClCpm->activeMasterNodeId = notificationBuffer->leader;
            gpClCpm->deputyNodeId = notificationBuffer->deputy;
        }
        /*
         * There could be more than 1 standby SC. 
         * Every none HA-state SC except the master is updated to become to standby SC.        
         */
        else if (gpClCpm->haState == CL_AMS_HA_STATE_NONE)
        {
            /*
             * Bug 4411:
             * Added the if-else block.
             * Calling the clAmsStart only if both the callback pointers
             * are not NULL.
             * FIXME: This change is sort of workaround for 2.2.
             * Neat solution is to protect gpClCpm structure and fields properly
             */
            if ((gpClCpm->amsToCpmCallback != NULL) &&
                (gpClCpm->cpmToAmsCallback != NULL))
            {
                clLogDebug(CPM_LOG_AREA_CPM, CPM_LOG_CTX_CPM_AMS,
                           "Starting AMS in standby mode...");

                rc = clAmsStart(&gAms,CL_AMS_INSTANTIATE_MODE_STANDBY);
                /*
                 * Bug 4092:
                 * If the AMS initialize fails then do the 
                 * self shut down.
                 */
                if (CL_OK != rc)
                {
                    clLogCritical(CPM_LOG_AREA_CPM, CPM_LOG_CTX_CPM_AMS,"Unable to initialize AMS, error = [%#x]", rc);

                    gpClCpm->amsToCpmCallback = NULL;
                    cpmRestart(NULL,NULL);
                    return;
                }
            }
            else
            {
                rc = CL_CPM_RC(CL_ERR_NULL_POINTER);
                 
                if (!gpClCpm->polling)
                {
                    clLogCritical(CPM_LOG_AREA_CPM, CPM_LOG_CTX_CPM_AMS,"AMS finalize called before AMS initialize during node shutdown.");
                }
                else
                {
                    clLogCritical(CPM_LOG_AREA_CPM, CPM_LOG_CTX_CPM_AMS,"Unable to initialize AMS, error = [%#x]", rc);
                    cpmRestart(NULL,NULL);
                }
                return;
            }

            gpClCpm->haState = CL_AMS_HA_STATE_STANDBY;
            gpClCpm->activeMasterNodeId = notificationBuffer->leader;
            gpClCpm->deputyNodeId = notificationBuffer->deputy;
            if(gpClCpm->bmTable->currentBootLevel == pCpmLocalInfo->defaultBootLevel)
            {
                cpmInitializeStandby();
            }
        }
        else
        {
            gpClCpm->activeMasterNodeId = notificationBuffer->leader;
            gpClCpm->deputyNodeId = notificationBuffer->deputy;
        }

        clLogNotice(CPM_LOG_AREA_CPM, CPM_LOG_CTX_CPM_CPM,
                    "HA state of node [%s] with node ID [%d] is [%s], "
                    "Master node is [%d]",
                    pCpmLocalInfo->nodeName,
                    pCpmLocalInfo->nodeId,
                    gpClCpm->haState == CL_AMS_HA_STATE_ACTIVE  ? "Active":
                    gpClCpm->haState == CL_AMS_HA_STATE_STANDBY ? "Standby":
                    "None",
                    gpClCpm->activeMasterNodeId);
    }
    else
    {
        /*
         * Always update the deputy node ID.  It may be that this
         * path is reached because a deputy node failed.
         */
        gpClCpm->deputyNodeId = notificationBuffer->deputy;

        if (CL_CPM_IS_ACTIVE())
        {
            if(notificationBuffer->notification && 
               notificationBuffer->numberOfItems == 1)
            {

                if (CL_GMS_NODE_LEFT ==
                    notificationBuffer->notification->clusterChange)
                {
                    cpmFailoverNode(notificationBuffer->notification->
                                    clusterNode.nodeId, CL_FALSE);
                }
                else
                {
                    clLogNotice(CPM_LOG_AREA_CPM, CPM_LOG_CTX_CPM_AMS, 
                                "Ignoring notification of type [%d] for node [%d]",
                                notificationBuffer->notification->clusterChange,
                                notificationBuffer->notification->clusterNode.nodeId);
                }
            }
            else if(notificationBuffer->notification)
            {
                clLogNotice(CPM_LOG_AREA_CPM, CPM_LOG_CTX_CPM_AMS, 
                            "Ignoring notification with number of items [%d], first type [%d]",
                            notificationBuffer->numberOfItems,
                            notificationBuffer->notification->clusterChange);
            }
        }
        else if ((gpClCpm->haState == CL_AMS_HA_STATE_NONE) && ( (ClInt32T) notificationBuffer->deputy == pCpmLocalInfo->nodeId))
        {
            if(CL_GMS_NODE_JOINED ==
               notificationBuffer->notification->clusterChange)
            {
                cpmStandbyRecover(notificationBuffer);
            }
            else if(gpClCpm->bmTable->currentBootLevel == pCpmLocalInfo->defaultBootLevel)
            {
                cpmStandbyRecover(notificationBuffer);
                cpmInitializeStandby();
            }
        }
    }
    return ;
}
ClRcT cpmInvocationAddKey(ClUint32T cbType,
                          void *data,
                          ClInvocationT invocationId,
                          ClUint32T flags)
{
    ClRcT rc = CL_OK;
    ClCpmInvocationT *temp = NULL;
    ClUint32T invocationKey = 0;

    if (cbType < 0x1LL || cbType >= CL_CPM_MAX_CALLBACK)
        CL_CPM_CHECK(CL_LOG_SEV_ERROR, ("Invalid parameter passed \n"),
                     CL_CPM_RC(CL_ERR_INVALID_PARAMETER));
    temp =
        (ClCpmInvocationT *) clHeapAllocate(sizeof(ClCpmInvocationT));
    if (temp == NULL)
        CL_CPM_CHECK(CL_LOG_SEV_ERROR, ("Unable to allocate memory \n"),
                     CL_CPM_RC(CL_ERR_NO_MEMORY));

    clOsalMutexLock(gpClCpm->invocationMutex);

    temp->invocation = invocationId;
    temp->data = data;
    temp->flags = flags; 

    CL_CPM_INVOCATION_KEY_GET(invocationId, invocationKey);

    rc = clCntNodeAdd(gpClCpm->invocationTable, (ClCntKeyHandleT)&temp->invocation,
                      (ClCntDataHandleT) temp, NULL);
    if (rc != CL_OK)
    {
        if(CL_GET_ERROR_CODE(rc) == CL_ERR_DUPLICATE)
        {
            clLogWarning("ADD", "INVOCATION", "Invocation entry [%#llx] already exists", invocationId);
            rc = CL_OK;
        }
        else
        {
            clLogError("ADD", "INVOCATION", "Invocation entry [%#llx] returned [%#x]",
                       invocationId, rc);
        }
        goto withLock;
    }

    /*
     * Try preventing reuse of the invocation key for new invocations.
     */
    if(gpClCpm->invocationKey <= invocationKey)
    {
        gpClCpm->invocationKey = invocationKey + 1;
    }

    clLogDebug("ADD", "INVOCATION", "Added entry for invocation [%#llx]", invocationId);
               
    clOsalMutexUnlock(gpClCpm->invocationMutex);
    return rc;

    withLock:
    clOsalMutexUnlock(gpClCpm->invocationMutex);

    failure:
    if (temp != NULL)
        clHeapFree(temp);

    return rc;
}
static ClRcT cpmComponentRmv(ClCharT *compName)
{
    ClRcT rc = CL_OK;
    ClUint16T compKey = 0;
    ClCntNodeHandleT hNode = 0;
    ClUint32T numNode = 0;
    ClCpmComponentT *comp = NULL;
    ClBoolT done = CL_NO;
    SaNameT entity = {0};

    if (!compName)
    {
        clLogError(CPM_LOG_AREA_CPM, CPM_LOG_CTX_CPM_MGM,
                   "NULL pointer passed.");
        goto failure;
    }

    rc = clCksm16bitCompute((ClUint8T *)compName,
                            strlen(compName),
                            &compKey);
    if (CL_OK != rc)
    {
        clLogError(CPM_LOG_AREA_CPM, CPM_LOG_CTX_CPM_MGM,
                   "Failed to compute checksum for component, "
                   "error [%#x]",
                   rc);
        goto failure;
    }
    saNameSet(&entity, compName);
    /*
     * Clear pending invocations for the component being removed.
     */
    (void)cpmInvocationClearCompInvocation(&entity);
    clOsalMutexLock(gpClCpm->compTableMutex);
    clOsalMutexLock(&gpClCpm->compTerminateMutex);

    rc = clCntNodeFind(gpClCpm->compTable,
                       (ClCntKeyHandleT)(ClWordT)compKey,
                       &hNode);
    if (CL_OK != rc)
    {
        clLogError(CPM_LOG_AREA_CPM, CPM_LOG_CTX_CPM_MGM,
                   "Failed to find component [%s], error [%#x]",
                   compName,
                   rc);
        goto unlock;
    }

    rc = clCntKeySizeGet(gpClCpm->compTable,
                         (ClCntKeyHandleT)(ClWordT)compKey,
                         &numNode);
    if (CL_OK != rc)
    {
        clLogError(CPM_LOG_AREA_CPM, CPM_LOG_CTX_CPM_MGM,
                   "Unable to get key size, error [%#x]",
                   rc);
        goto unlock;
    }

    while (numNode > 0)
    {
        rc = clCntNodeUserDataGet(gpClCpm->compTable,
                                  hNode,
                                  (ClCntNodeHandleT *) &comp);
        if (CL_OK != rc)
        {
            clLogError(CPM_LOG_AREA_CPM, CPM_LOG_CTX_CPM_MGM,
                       "Unable to get user data, error [%#x]",
                       rc);
            goto unlock;
        }

        if (!strncmp(compName,
                     comp->compConfig->compName,
                     CL_MAX_NAME_LENGTH-1))
        {
            clCntNodeDelete(gpClCpm->compTable, hNode);
            done = CL_YES;
            break;
        }

        if (--numNode)
        {
            rc = clCntNextNodeGet(gpClCpm->compTable, hNode, &hNode);
            if (CL_OK != rc)
            {
                break;
            }
        }
    }

    if (!done)
    {
        rc = CL_CPM_RC(CL_ERR_DOESNT_EXIST);
        goto unlock;
    }
    
    --gpClCpm->noOfComponent;

    clOsalMutexUnlock(&gpClCpm->compTerminateMutex);
    clOsalMutexUnlock(gpClCpm->compTableMutex);

    return CL_OK;

unlock:
    clOsalMutexUnlock(&gpClCpm->compTerminateMutex);
    clOsalMutexUnlock(gpClCpm->compTableMutex);
failure:
    return rc;
}
ClRcT cpmNodeAdd(ClCharT *nodeName)
{
    ClRcT rc = CL_OK;
    ClCpmLT *cpm = NULL;
    ClUint16T nodeKey = 0;
    ClCpmSlotInfoT slotInfo = {0};

    if (!nodeName)
    {
        clLogError(CPM_LOG_AREA_CPM, CPM_LOG_CTX_CPM_MGM, "NULL pointer passed.");
        goto failure;
    }

    clOsalMutexLock(gpClCpm->cpmTableMutex);
    rc = cpmNodeFindLocked((SaUint8T *)nodeName, &cpm);
    clOsalMutexUnlock(gpClCpm->cpmTableMutex);
    if (cpm)
    {
        clLogWarning(CPM_LOG_AREA_CPM, CPM_LOG_CTX_CPM_MGM, "Node [%s] already exists on this node.", nodeName);
        rc = CL_CPM_RC(CL_ERR_ALREADY_EXIST);
        goto failure;
    }

    cpm = (ClCpmLT*) clHeapAllocate(sizeof(ClCpmLT));
    if (!cpm)
    {
        clLogError(CPM_LOG_AREA_CPM, CPM_LOG_CTX_CPM_MGM,
                   "Unable to allocate memory");
        goto failure;
    }

    memset(cpm, 0, sizeof(ClCpmLT));
    
    strncpy(cpm->nodeName, nodeName, strlen(nodeName));
    
    rc = clCksm16bitCompute((ClUint8T *)cpm->nodeName,
                            strlen(cpm->nodeName),
                            &nodeKey);
    if (CL_OK != rc)
    {
        clLogError(CPM_LOG_AREA_CPM, CPM_LOG_CTX_CPM_MGM,
                   "Failed to compute checksum for node, "
                   "error [%#x]",
                   rc);
        goto failure;
    }

    /* 
     * Filling the CPML with defaults.  
     */

    saNameSet(&cpm->nodeType, nodeName);
    saNameSet(&cpm->nodeIdentifier, nodeName);
    /*
     * Set the class type to CLASS_C.
     */
    strncpy(cpm->classType, "CL_AMS_NODE_CLASS_C", sizeof(cpm->classType)-1);
    /*
     * Get the MOID of the master node. Assuming that node add is
     * only invoked on the master.
     */
    slotInfo.slotId = clIocLocalAddressGet();

    rc = clCpmSlotInfoGet(CL_CPM_SLOT_ID, &slotInfo);
    if(rc == CL_OK)
    {
        rc = cpmCorMoIdToMoIdNameGet(&slotInfo.nodeMoId, &cpm->nodeMoIdStr);
    }
    if(rc != CL_OK)
    {
        if((CL_GET_ERROR_CODE(rc) != CL_IOC_ERR_COMP_UNREACHABLE) && (CL_GET_ERROR_CODE(rc) != CL_ERR_NOT_EXIST) && (CL_GET_ERROR_CODE(rc) != CL_ERR_NOT_SUPPORTED))
        {
            goto failure;
        }
        else
        {
            rc = CL_OK;
            clLogWarning(CPM_LOG_AREA_CPM, CPM_LOG_CTX_CPM_MGM, "COR server not running so cannot discover the Node's MoId");
        }
    }

    clOsalMutexLock(gpClCpm->cpmTableMutex);

    rc = clCntNodeAdd(gpClCpm->cpmTable,
                      (ClCntKeyHandleT)(ClWordT)nodeKey,
                      (ClCntDataHandleT) cpm,
                      NULL);
    if (CL_OK != rc)
    {
        clLogError(CPM_LOG_AREA_CPM, CPM_LOG_CTX_CPM_MGM,
                   "Failed to add node to the CPM node table, "
                   "error [%#x]",
                   rc);
        clOsalMutexUnlock(gpClCpm->cpmTableMutex);
        goto failure;
    }

    ++gpClCpm->noOfCpm;

    clOsalMutexUnlock(gpClCpm->cpmTableMutex);

    /*
     * Add this to the slotinfo.
     */

    clOsalMutexLock(&gpClCpm->cpmMutex);
    rc = cpmSlotClassAdd(&cpm->nodeType, &cpm->nodeIdentifier, 0);
    clOsalMutexUnlock(&gpClCpm->cpmMutex);

    if(rc != CL_OK)
    {
        clLogError(CPM_LOG_AREA_CPM, CPM_LOG_CTX_CPM_MGM,
                   "Node [%s] class add returned [%#x]", cpm->nodeType.value, rc);
    }

    clLogNotice("DYN", "NODE", "Node [%s] added to the cpm table with identity [%.*s]",
                cpm->nodeName, cpm->nodeIdentifier.length, cpm->nodeIdentifier.value);
                
    return CL_OK;

    failure:
    return rc;
}
ClRcT cpmCompParseArgs(ClCpmCompConfigT *compConfig, ClCharT *cmd, ClUint32T *pArgIndex)
{
    ClCharT tmp[CL_MAX_NAME_LENGTH] = {0};
    ClCharT imageName[CL_MAX_NAME_LENGTH];
    ClCharT *c = NULL;
    ClCharT *saveptr = NULL;
    ClUint32T i = 0;
    ClUint32T argIndex = 0;
    ClRcT rc = CL_OK;

    if(pArgIndex) *pArgIndex = 0;

    strncpy(tmp, cmd, CL_MAX_NAME_LENGTH-1);

    for(i = 0; compConfig->argv[i]; ++i)
    {
        clHeapFree(compConfig->argv[i]);
        compConfig->argv[i] = NULL;
    }

    i = 0;

    if(cpmIsValgrindBuild(cmd)) 
    { 
        cpmModifyCompArgs(compConfig, &i);
    }
    argIndex = i;
    c = strtok_r(tmp, " ", &saveptr);
    while (c && (i < CPM_MAX_ARGS - 1))
    {
        ClUint32T len = strlen(c);
        if(i == argIndex && *c != '/')
        {
            ClCharT *binPath = getenv(CL_ASP_BINDIR_PATH);
            snprintf(imageName, sizeof(imageName)-1, "%s%s%s", 
                     binPath ? binPath : "", binPath ? "/" : "", c);
            len = strlen(imageName);
            c = imageName;
        }
        compConfig->argv[i] = (ClCharT*) clHeapAllocate(len + 1);
        if (!compConfig->argv[i])
        {
            clLogError(CPM_LOG_AREA_CPM, CPM_LOG_CTX_CPM_MGM,
                       "Unable to allocate memory");
            rc = CL_CPM_RC(CL_ERR_NO_MEMORY);
            goto failure;
        }

        strcpy(compConfig->argv[i], c);
        ++i;

        c = strtok_r(NULL, " ", &saveptr);
    }
    compConfig->argv[i] = NULL;

    if(compConfig->argv[argIndex])
    {
        strncpy(compConfig->instantiationCMD,
                compConfig->argv[argIndex],
                CL_MAX_NAME_LENGTH-1);
    }

    if(pArgIndex) *pArgIndex = i;

    return CL_OK;
    
failure:
    return rc;
}
ClRcT cpmCompParseArgs(ClCpmCompConfigT *compConfig, ClCharT *cmd, ClUint32T *pArgIndex)
{
    ClCharT imageName[CL_MAX_NAME_LENGTH];
    ClUint32T i = 0;
    ClUint32T argIndex = 0;
    ClRcT rc = CL_OK;
    ClCharT *saveptr = NULL;
    ClCharT *token = cmd;
    ClBoolT doubleQuote = CL_FALSE;

    if(pArgIndex) *pArgIndex = 0;

    for(i = 0; compConfig->argv[i]; ++i)
    {
        clHeapFree(compConfig->argv[i]);
        compConfig->argv[i] = NULL;
    }

    i = 0;

    if(cpmIsValgrindBuild(cmd)) 
    { 
        cpmModifyCompArgs(compConfig, &i);
    }
    argIndex = i;
#if 0
    c = strtok_r(tmp, " ", &saveptr);
    while (c && (i < CPM_MAX_ARGS - 1))
    {
        ClUint32T len = strlen(c);
        if(i == argIndex && *c != '/')
        {
            ClCharT *binPath = getenv(CL_ASP_BINDIR_PATH);
            snprintf(imageName, sizeof(imageName)-1, "%s%s%s", 
                     binPath ? binPath : "", binPath ? "/" : "", c);
            len = strlen(imageName);
            c = imageName;
        }
        compConfig->argv[i] = (ClCharT*) clHeapAllocate(len + 1);
        if (!compConfig->argv[i])
        {
            clLogError(CPM_LOG_AREA_CPM, CPM_LOG_CTX_CPM_MGM,
                       "Unable to allocate memory");
            rc = CL_CPM_RC(CL_ERR_NO_MEMORY);
            goto failure;
        }

        strcpy(compConfig->argv[i], c);
        ++i;

        c = strtok_r(NULL, " ", &saveptr);
    }
#else
    while (*token)
    {
      // Remove leading spaces
      while (*token == ' ')
        ++token;

      saveptr = token;
      while (*saveptr)
      {
        if (*saveptr != '\"' || !doubleQuote)
        {
          ++saveptr;
          if (*saveptr == '\"')
          {
            doubleQuote = CL_TRUE;
            break;
          }
          else if (*saveptr == ' ')
          {
            break;
          }
        }
      }

      // if possible double quotes string, scan for next one
      if (doubleQuote)
      {
        char quote = *saveptr++;
        while (*saveptr)
          if (*saveptr != quote)
            ++saveptr;
          else if (saveptr[1] == quote)
            saveptr += 2;
          else
          {
            ++saveptr;
            break;
          }
        doubleQuote = CL_FALSE;
      }

      ClCharT tmp[CL_MAX_NAME_LENGTH] = {0};
      strncpy(tmp, token, (saveptr - token));
      ClUint32T len = strlen(tmp);
      if (i == argIndex && *tmp != '/')
      {
        ClCharT *binPath = getenv(CL_ASP_BINDIR_PATH);
        snprintf(imageName, sizeof(imageName) - 1, "%s%s%s", binPath ? binPath : "", binPath ? "/" : "", tmp);
        len = strlen(imageName);
        strncpy(tmp, imageName, CL_MAX_NAME_LENGTH - 1);
        tmp[len] = '\0';
      }

      compConfig->argv[i] = (ClCharT *)clHeapAllocate(len + 1);
      if (!compConfig->argv[i])
      {
          rc = CL_CPM_RC(CL_ERR_NO_MEMORY);
          goto failure;
      }

      strcpy(compConfig->argv[i], tmp);
      ++i;

      token = saveptr;
    }
#endif

    compConfig->argv[i] = NULL;

    if(compConfig->argv[argIndex])
    {
        strncpy(compConfig->instantiationCMD,
                compConfig->argv[argIndex],
                CL_MAX_NAME_LENGTH-1);
    }

    if(pArgIndex) *pArgIndex = i;

    return CL_OK;
    
failure:
    return rc;
}
ClRcT clCpmComponentReport(ClUint32T argc, ClCharT *argv[], ClCharT **retStr)
{
    ClNameT compName;
    ClCharT buffer[100] = "\0";
    ClRcT rc = CL_OK;
    ClTimeT time;
    ClAmsLocalRecoveryT recommendedRecovery;
    ClUint32T alarmHandle = 0;
    ClUint32T length = 0;

    if (!strcasecmp("compReport", argv[0]))
    {
        if (argc != 4)
        {
            sprintf(buffer,
                    "Usage: %s <Component Name> <time> <recommondedRecovery>\n, ",
                    argv[0]);
            rc = CL_CPM_RC(CL_ERR_INVALID_PARAMETER);
            goto level1;
        }

        /*
         * Source Info 
         */
        strcpy(compName.value, argv[1]);
        compName.length = strlen(argv[1]);
        /*
         * with All parameters
         */
        time = (ClTimeT) cpmCliStrToInt(argv[2]);
        recommendedRecovery = (ClAmsLocalRecoveryT) cpmCliStrToInt(argv[3]);

        rc = clCpmComponentFailureReport(0, &compName, time,
                                         recommendedRecovery, alarmHandle);
        if (rc == CL_OK)
            sprintf(buffer, "%s\n", "Sucessfully sent request for the "
                    "failure report command");
        else
            sprintf(buffer, "Failed to report error %x\n", rc);
    }
    else if (!strcasecmp("compClear", argv[0]))
    {
        if (argc != 2)
        {
            sprintf(buffer,
                    "Usage: %s <Component Name>\n",
                    argv[0]);
            rc = CL_CPM_RC(CL_ERR_INVALID_PARAMETER);
            goto level1;
        }
        strcpy(compName.value, argv[1]);
        compName.length = strlen(argv[1]);

        rc = clCpmComponentFailureClear(0, &compName);
        if (rc == CL_OK)
            sprintf(buffer, "%s\n", "Sucessfully sent request for the "
                    "failure clear command");
        else
            sprintf(buffer, "Failed to report clear of an error %x\n", rc);
    }
    else
    {
        rc = CL_CPM_RC(CL_ERR_DOESNT_EXIST);
        sprintf(buffer, "%s", "Unknown Command ............");
    }

  level1:
    length = strlen(buffer) + 1;
    *retStr = (ClCharT *) clHeapAllocate(length);
    if (*retStr != NULL)
        strcpy(*retStr, buffer);
    else
        rc = CL_CPM_RC(CL_ERR_NO_MEMORY);

    return rc;
}
ClRcT clCpmSlotInfoGet(ClCpmSlotInfoFieldIdT flag, ClCpmSlotInfoT *slotInfo)
{
    ClRcT rc = CL_OK;
    ClIocNodeAddressT masterIocAddress = 0;
    ClCpmSlotInfoRecvT  slotInfoRecv = { CL_CPM_SLOT_ID};
    ClUint32T           bufSize = 0;
    
    /* make a SYNC RMD to CPM/G master */
    
    rc = clCpmMasterAddressGet(&masterIocAddress);
    if (rc != CL_OK)
        goto failure;

    slotInfoRecv.flag = flag;
    switch(slotInfoRecv.flag)
    {
        case CL_CPM_SLOT_ID:
        {
            slotInfoRecv.slotId = slotInfo->slotId;
            break;
        }
        case CL_CPM_IOC_ADDRESS:
        {
            slotInfoRecv.nodeIocAddress = slotInfo->nodeIocAddress;
            break;
        }
#ifdef USE_COR        
        case CL_CPM_NODE_MOID:
        {
            slotInfoRecv.nodeMoIdStr.length = 0;
            slotInfoRecv.nodeMoIdStr.value[0] = 0;                
            rc = clCorMoIdToMoIdNameGet(&slotInfo->nodeMoId, &slotInfoRecv.nodeMoIdStr);
            CPM_CLIENT_CHECK(CL_LOG_SEV_ERROR,("MoIdToMoIdNameGet Failed, rc=[0x%x]\n", rc), rc);
            break;
        }
#endif        
        case CL_CPM_NODENAME:
        {
            memcpy(&slotInfoRecv.nodeName, &slotInfo->nodeName, sizeof(SaNameT));
            break;
        }
        default:
        {
            rc = CL_CPM_RC(CL_ERR_INVALID_PARAMETER);
            clLogError(CPM_LOG_AREA_CPM,CL_LOG_CONTEXT_UNSPECIFIED,
                       "Invalid flag passed, rc=[0x%x]\n", rc);
            goto failure;
            break;
        }
    }

    rc = clCpmClientRMDSyncNew(masterIocAddress, CPM_SLOT_INFO_GET,
                               (ClUint8T *) &slotInfoRecv, sizeof(ClUint32T),
                               (ClUint8T *) &slotInfoRecv, &bufSize,
                               CL_RMD_CALL_NEED_REPLY, 0, 0, 0,
                               MARSHALL_FN(ClCpmSlotInfoRecvT, 4, 0, 0),
                               UNMARSHALL_FN(ClCpmSlotInfoRecvT, 4, 0, 0));
    
    CPM_CLIENT_CHECK(CL_LOG_SEV_ERROR, ("Unable to find information about given entity, rc=[0x%x]\n", rc), rc);

    switch(slotInfoRecv.flag)
    {
        case CL_CPM_SLOT_ID:
        {
            slotInfo->nodeIocAddress = slotInfoRecv.nodeIocAddress;
#ifdef USE_COR        
            rc = clCorMoIdNameToMoIdGet(&slotInfoRecv.nodeMoIdStr, &slotInfo->nodeMoId);
            CPM_CLIENT_CHECK(CL_LOG_SEV_ERROR,
                    ("MoIdNameToMoIdGet Failed, rc=[0x%x]\n", rc), rc);
#endif            
            memcpy(&slotInfo->nodeName, &slotInfoRecv.nodeName, sizeof(SaNameT));

            break;
        }
        case CL_CPM_IOC_ADDRESS:
        {
            slotInfo->slotId = slotInfoRecv.slotId;
#ifdef USE_COR  
            rc = clCorMoIdNameToMoIdGet(&slotInfoRecv.nodeMoIdStr, &slotInfo->nodeMoId);
            CPM_CLIENT_CHECK(CL_LOG_SEV_ERROR,
                    ("MoIdNameToMoIdGet Failed, rc=[0x%x]\n", rc), rc);
#endif
            memcpy(&slotInfo->nodeName, &slotInfoRecv.nodeName, sizeof(SaNameT));

            break;
        }
        case CL_CPM_NODE_MOID:
        {
            slotInfo->slotId = slotInfoRecv.slotId;
            
            slotInfo->nodeIocAddress = slotInfoRecv.nodeIocAddress;
            
            memcpy(&slotInfo->nodeName, &slotInfoRecv.nodeName, sizeof(SaNameT));

            break;
        }
        case CL_CPM_NODENAME:
        {
            slotInfo->slotId = slotInfoRecv.slotId;

            slotInfo->nodeIocAddress = slotInfoRecv.nodeIocAddress;
#ifdef USE_COR 
            rc = clCorMoIdNameToMoIdGet(&slotInfoRecv.nodeMoIdStr, &slotInfo->nodeMoId);
            CPM_CLIENT_CHECK(CL_LOG_SEV_ERROR,
                    ("MoIdNameToMoIdGet Failed, rc=[0x%x]\n", rc), rc);
#endif
            break;
        }
        default:
        {
            rc = CL_CPM_RC(CL_ERR_INVALID_PARAMETER);
            clLogError(CPM_LOG_AREA_CPM,CL_LOG_CONTEXT_UNSPECIFIED,
                       "Invalid flag passed, rc=[0x%x]\n", rc);
            goto failure;
            break;
        }
    }

    return rc;

failure:
    return rc;
}
ClRcT clCpmCompGet(ClUint32T argc, ClCharT *argv[], ClCharT **retStr)
{
    ClRcT rc = CL_OK;
    ClNameT compName = { 0 };
    ClIocAddressT compAddress;
    ClUint32T compId = 0;
    ClCharT buffer[2048] = "\0";
    ClUint32T length = 0;
    ClIocNodeAddressT nodeAddress;

    if (!strcasecmp("compAddressGet", argv[0]))
    {
        if (argc != THREE_ARGUMENT)
        {
            sprintf(buffer, "%s",
                    "Usage: compAddressGet <CompName> <nodeIocAddress>\n"
                    "\tcompName[STRING] - component Name\n"
                    "\tnodeIocAddress[DEC] - node ioc Address, where the component exist\n");
            rc = CL_CPM_RC(CL_ERR_INVALID_PARAMETER);
            goto done;
        }
        strcpy(compName.value, argv[1]);
        compName.length = strlen(argv[1]);
        nodeAddress = (ClIocNodeAddressT) cpmCliStrToInt(argv[2]);
        rc = clCpmComponentAddressGet(nodeAddress, &compName, &compAddress);
        if (rc == CL_OK)
            sprintf(buffer, "Address %d Port %x\n",
                    compAddress.iocPhyAddress.nodeAddress,
                    compAddress.iocPhyAddress.portId);
        else
            sprintf(buffer, "Failed get component Address, rc = 0x%x", rc);
    }
    else if (!strcasecmp("compIdGet", argv[0]))
    {
        if (argc != TWO_ARGUMENT)
        {
            sprintf(buffer, "%s",
                    "Usage: compIdGet <CompName> \n"
                    "\tcompName[STRING] - component Name\n");
            rc = CL_CPM_RC(CL_ERR_INVALID_PARAMETER);
           goto done;
        }
        strcpy(compName.value, argv[1]);
        compName.length = strlen(argv[1]);
        rc = clCpmComponentIdGet(0, &compName, &compId);
        if (rc == CL_OK)
            sprintf(buffer, "compId is %d\n", compId);
        else
            sprintf(buffer, "Failed get component Id, rc = 0x%x", rc);
    }
    else if (!strcasecmp("compPIDGet", argv[0]))
    {
        if (argc != TWO_ARGUMENT)
        {
            sprintf(buffer, "%s",
                    "Usage: compPidGet <CompName> \n"
                    "\tcompName[STRING] - component Name\n");
            rc = CL_CPM_RC(CL_ERR_INVALID_PARAMETER);
            goto done;
        }
        strcpy(compName.value, argv[1]);
        compName.length = strlen(argv[1]);
        rc = clCpmComponentPIDGet(&compName, &compId);
        if (rc == CL_OK)
            sprintf(buffer, "compPId is %d\n", compId);
        else
            sprintf(buffer, "Failed get component PID, rc = 0x%x", rc);
    }
    else if (!strcasecmp("compTraceGet", argv[0]))
    {
        ClPtrT ppOutMem = NULL;
        ClUint32T segmentSize = 0;
        ClFdT fd = 0;
#ifndef POSIX_BUILD
        ClCharT compShmSegment[CL_MAX_NAME_LENGTH];
        segmentSize = getpagesize();
        if (argc != TWO_ARGUMENT)
        {
            sprintf(buffer, "%s",
                    "Usage: compTraceGet <CompName> \n"
                    "\tcompName[STRING] - component Name \n");
            rc = CL_CPM_RC(CL_ERR_INVALID_PARAMETER);
            goto done;
        }
        strcpy(compName.value, argv[1]);
        snprintf(compShmSegment, sizeof(compShmSegment), "/CL_%s_exception_%d", compName.value, clIocLocalAddressGet());
        rc = clOsalShmOpen(compShmSegment, O_RDONLY, 0777, &fd);
        if(rc == CL_OK)
        {
            rc = clOsalMmap(0, segmentSize, PROT_READ, MAP_PRIVATE, fd, 0, &ppOutMem);
        }
#endif
        if (ppOutMem)
        {
            sprintf(buffer, "%s\n", (ClCharT*)ppOutMem);
            clOsalMunmap(ppOutMem, segmentSize);
            close(fd);
        }
        else
            sprintf(buffer, "%s\n", "Unable to get the component Stack Trace");
    }
  done:
    length = strlen(buffer) + 1;
    *retStr = (ClCharT *) clHeapAllocate(length);
    if (*retStr != NULL)
        strcpy(*retStr, buffer);
    else
        rc = CL_CPM_RC(CL_ERR_NO_MEMORY);

    return rc;
}