Esempio n. 1
0
/*
 *  ======== NullConverter_issue ========
 */
Void NullConverter_issue(NullConverter_Object *obj, DriverTypes_Packet *packet, 
    Error_Block *eb)
{
    List_put(NullConverter_Instance_State_packetList(obj), 
                (List_Elem *)packet);
    obj->cbFxn(obj->cbArg);
}
/*!
 *  @brief      Insert an entry into the Translation Table
 *
 *  @param      da      Device address
 *  @param      ua      User address
 *  @param      size    Buffer size
 *
 *  @sa         _SysLinkMemUtils_removeMapElement
 */
static Int32
_SysLinkMemUtils_insertMapElement (Ptr da, Ptr ua, UInt32 size)
{
    AddrNode      * node;
    Int32           status = PROCMGR_SUCCESS;

    GT_3trace (curTrace, GT_ENTER, "_SysLinkMemUtils_insertMapElement", da, ua,
                size);

    node = Memory_alloc (NULL, sizeof (AddrNode), 0);
    if (!node) {
        status = PROCMGR_E_MEMORY;
#if !defined(SYSLINK_BUILD_OPTIMIZE)
        GT_setFailureReason (curTrace,
                             GT_4CLASS,
                             (Char *)__func__,
                             status,
                             "Error allocating node memory!");
#endif /* if !defined(SYSLINK_BUILD_OPTIMIZE) */
    }
    else {
        node->ua = ua;
        node->da = da;
        node->size = size;
        OsalSemaphore_pend (SysLinkMemUtils_module->semList,
                            OSALSEMAPHORE_WAIT_FOREVER);
        List_put (SysLinkMemUtils_module->addrTable, &node->elem);
        OsalSemaphore_post (SysLinkMemUtils_module->semList);
    }

    GT_1trace (curTrace, GT_LEAVE, "_SysLinkMemUtils_insertMapElement", status);

    return status;
}
Esempio n. 3
0
/*
 *  ======== Stream_postInit ========
 */
Int Stream_postInit(Stream_Object *obj, Error_Block *eb)
{
    List_Handle             freeList;
    UInt                    i, len;
    IDriver_Handle          drvHandle;
    DriverAdapter_Params    adapPrms;
    
    freeList = Stream_Instance_State_freeList(obj);
    /* 
     * Split the buffer into packets and add to freeList
     */
    for (i = 0; i < obj->maxIssues; i++) {
        List_put(freeList, (List_Elem *)&obj->packets[i]);
    }
    
    len = Stream_match(obj->name, &obj->convHandle, eb);    
        
    if (len == 0) {
        /* Look in DriverTable */
        obj->drvAdapHdl = TRUE;
        
        len = DriverTable_match(obj->name, &drvHandle, eb);
        if (len == 0) {
            /* The name was not found */
            Error_raise(eb, Stream_E_notFound, obj->name, 0);
            return (3);
        }
        else {
            DriverAdapter_Params_init(&adapPrms);
            adapPrms.driverHandle = drvHandle;
            obj->convHandle = DriverAdapter_Handle_upCast(
                DriverAdapter_create(&adapPrms, eb));
            if (obj->convHandle == NULL) {
                return (4);
            }
        }
    }
    else {
        obj->drvAdapHdl = FALSE;
    }
      
    IConverter_open(obj->convHandle, ((obj->name) + len), obj->mode, 
        obj->chanParams, Stream_internalCallback, (UArg)obj, eb); 
    
    if (Error_check(eb)) {
        return (5);
    }
    
    return (0);
}
Esempio n. 4
0
/*
 *  ======== DriverAdapter_callback ========
 *  This function is called by the driver when I/O completes.
 */
Void DriverAdapter_callback(UArg cbArg, DriverTypes_Packet *packet)
{
    DriverAdapter_Object *obj = (DriverAdapter_Object *)cbArg;
    List_Handle fromDriver;

    Stream_completedLog((UArg)packet->addr, (UArg)packet->size,
        (UArg)packet->arg);
    
    fromDriver = DriverAdapter_Instance_State_fromDriver(obj);
        
    /* put packet in fromDriver queue for collection by reclaim */
    List_put(fromDriver, (List_Elem *)packet);

    /* callback into top layer */
    obj->cbFxn(obj->cbArg);
}
Esempio n. 5
0
/*
 *  ======== Notify_registerEvent ========
 */
Int Notify_registerEvent(UInt16                 procId,
                         UInt16                 lineId,
                         UInt32                 eventId,
                         Notify_FnNotifyCbck    fnNotifyCbck,
                         UArg                   cbckArg)
{
    UInt32               strippedEventId = (eventId & 0xFFFF);
    UInt16 clusterId =   ti_sdo_utils_MultiProc_getClusterId(procId);
    Int                  status;
    ti_sdo_ipc_Notify_Object        *obj;
    UInt                 modKey;
    List_Handle          eventList;
    ti_sdo_ipc_Notify_EventListener *listener;
    Bool                 listWasEmpty;
    Error_Block          eb;

    Assert_isTrue(procId < ti_sdo_utils_MultiProc_numProcessors &&
                  lineId < ti_sdo_ipc_Notify_numLines, ti_sdo_ipc_Notify_A_invArgument);
    Assert_isTrue(strippedEventId < ti_sdo_ipc_Notify_numEvents,
                  ti_sdo_ipc_Notify_A_invArgument);
    Assert_isTrue(ISRESERVED(eventId), ti_sdo_ipc_Notify_A_reservedEvent);

    Error_init(&eb);

    modKey = Gate_enterModule();

    obj = (ti_sdo_ipc_Notify_Object *)
          Notify_module->notifyHandles[clusterId][lineId];

    Assert_isTrue(obj != NULL, ti_sdo_ipc_Notify_A_notRegistered);

    /* Allocate a new EventListener */
    listener = Memory_alloc(ti_sdo_ipc_Notify_Object_heap(),
                            sizeof(ti_sdo_ipc_Notify_EventListener), 0, &eb);
    if (listener == NULL) {
        /* Listener memory allocation failed.  Leave module gate & return */
        Gate_leaveModule(modKey);

        return (Notify_E_MEMORY);
    }

    listener->callback.fnNotifyCbck = (Fxn)fnNotifyCbck;
    listener->callback.cbckArg = cbckArg;

    eventList = List_Object_get(obj->eventList, strippedEventId);

    /*
     *  Store whether the list was empty so we know whether to register the
     *  callback
     */
    listWasEmpty = List_empty(eventList);

    /*
     *  Need to atomically add to the list using the system gate because
     *  Notify_exec might preempt List_remove.  List_put is atomic.
     */
    List_put(eventList, (List_Elem *)listener);

    if (listWasEmpty) {
        /*
         *  Registering this event for the first time.  Need to register the
         *  callback function.
         */
        status = Notify_registerEventSingle(procId, lineId, eventId,
                                            Notify_execMany, (UArg)obj);

        /* Notify_registerEventSingle should always succeed */
        Assert_isTrue(status == Notify_S_SUCCESS,
                      ti_sdo_ipc_Notify_A_internal);
    }

    status = Notify_S_SUCCESS;

    Gate_leaveModule(modKey);

    return (status);
}
Esempio n. 6
0
/*
 *  ======== Stream_reclaim ========
 */
SizeT Stream_reclaim(Stream_Object *obj, Ptr *bufp, UInt timeout, UArg *arg, 
    Error_Block *eb)
{
    DriverTypes_Packet  *packet = NULL;
    List_Handle         freeList;
    UInt                key;
    
    if (obj->issued == 0) {
        Error_raise(eb, Stream_E_noBuffersIssued, 0, 0);
        return (0);
    }

    while (obj->ready == 0) {
        if (!Sync_wait(obj->complete, timeout, eb)) {
            if (timeout != 0) {
                Error_raise(eb, Stream_E_timeout, timeout, 0);
            }
            return (0);
        }
    };
    IConverter_reclaim(obj->convHandle, &packet, eb);

    if (arg != NULL) {
        *arg = packet->arg;
    }

    /* bufp is NULL in Stream_read and Stream_write. */
    if (bufp != NULL) {
        *bufp = packet->addr;
    }

    key = Hwi_disable();
    obj->ready--;
    Hwi_restore(key);

    obj->issued--;

    /* 
     * re-signal if more buffers are ready
     * This is required in the case of ISyncEvent and ISyncSwi to allow 
     * clients to reclaim a single buffer and not force them to bleed the 
     * Stream. In the case of ISyncSem , this re-signal is an overhead
     */

    if (obj->ready > 0) {
        Sync_signal(obj->complete);
    }

    freeList = Stream_Instance_State_freeList(obj);

    /* recycle packet back onto free list */
    List_put(freeList, (List_Elem *)packet);

    if ((packet->error != NULL) &&
        (packet->error != DriverTypes_EABORTED)) {
        Error_raise(eb, packet->error, packet->status, 0);
        return (0);
    }
    else {
        return (packet->size);
    }
}
Esempio n. 7
0
/*
 *  ======== MessageQ_put ========
 */
Int MessageQ_put(MessageQ_QueueId queueId, MessageQ_Msg msg)
{
    IMessageQTransport_Handle transport;
    MessageQ_QueueIndex dstProcId = (MessageQ_QueueIndex)(queueId >> 16);
    List_Handle       listHandle;
    Int               status;
    UInt              priority;
#ifndef xdc_runtime_Log_DISABLE_ALL
    UInt16            flags;
    UInt16            seqNum;
    UInt16            srcProc;
#endif
    ti_sdo_ipc_MessageQ_Object   *obj;

    Assert_isTrue((msg != NULL), ti_sdo_ipc_MessageQ_A_invalidMsg);    
    
    msg->dstId   = (UInt16)(queueId);
    msg->dstProc = (UInt16)(queueId >> 16);
    
    if (dstProcId != MultiProc_self()) {
        /* assert that dstProcId is valid */
        Assert_isTrue(dstProcId < ti_sdo_utils_MultiProc_numProcessors,
                      ti_sdo_ipc_MessageQ_A_procIdInvalid);
        
        /* Put the high and urgent messages to the high priority transport */
        priority = (UInt)((msg->flags) & 
            ti_sdo_ipc_MessageQ_TRANSPORTPRIORITYMASK);

        /* Call the transport associated with this message queue */
        transport = MessageQ_module->transports[dstProcId][priority];
        if (transport == NULL) {
            /* Try the other transport */
            priority = !priority;
            transport = MessageQ_module->transports[dstProcId][priority];
        }
        
        /* assert transport is not null */
        Assert_isTrue(transport != NULL, 
            ti_sdo_ipc_MessageQ_A_unregisteredTransport);

#ifndef xdc_runtime_Log_DISABLE_ALL
        /* use local vars so msg does not get cached after put */
        flags = msg->flags;

        if ((ti_sdo_ipc_MessageQ_traceFlag) ||
            (flags & ti_sdo_ipc_MessageQ_TRACEMASK) != 0) {
            /* use local vars so msg does not get cached after put */
            seqNum  = msg->seqNum;
            srcProc = msg->srcProc;
        }
#endif

        /* put msg to remote processor using transport */
        if (IMessageQTransport_put(transport, msg)) {
            status = MessageQ_S_SUCCESS;

#ifndef xdc_runtime_Log_DISABLE_ALL
            /* if trace enabled */
            if ((ti_sdo_ipc_MessageQ_traceFlag) ||
                (flags & ti_sdo_ipc_MessageQ_TRACEMASK) != 0) {                    
                Log_write4(ti_sdo_ipc_MessageQ_LM_putRemote, (UArg)(msg), 
                          (UArg)(seqNum), (UArg)(srcProc),
                          (UArg)(dstProcId));
            }
#endif
        }
        else {
            status = MessageQ_E_FAIL;
        }       
    }
    else {
        /* Assert queueId is valid */
        Assert_isTrue((UInt16)queueId < MessageQ_module->numQueues,
                      ti_sdo_ipc_MessageQ_A_invalidQueueId);

        /* It is a local MessageQ */
        obj = MessageQ_module->queues[(UInt16)(queueId)];

        /* Assert object is not NULL */
        Assert_isTrue(obj != NULL, ti_sdo_ipc_MessageQ_A_invalidObj);

        if ((msg->flags & MessageQ_PRIORITYMASK) == MessageQ_URGENTPRI) {
            listHandle = ti_sdo_ipc_MessageQ_Instance_State_highList(obj);
            List_putHead(listHandle, (List_Elem *)msg);
        }
        else {
            if ((msg->flags & MessageQ_PRIORITYMASK) == MessageQ_NORMALPRI) {
                listHandle = ti_sdo_ipc_MessageQ_Instance_State_normalList(obj);
            }
            else {
                listHandle = ti_sdo_ipc_MessageQ_Instance_State_highList(obj);
            }
            /* put on the queue */
            List_put(listHandle, (List_Elem *)msg);
        }

        ISync_signal(obj->synchronizer);

        status = MessageQ_S_SUCCESS;

        if ((ti_sdo_ipc_MessageQ_traceFlag) ||
            (msg->flags & ti_sdo_ipc_MessageQ_TRACEMASK) != 0) {
            Log_write4(ti_sdo_ipc_MessageQ_LM_putLocal, (UArg)(msg), 
                       (UArg)(msg->seqNum), (UArg)(msg->srcProc), (UArg)(obj));
        }
    }

    return (status);
}
Void ListTest(Void)
{
    List_Params listParams;
    List_Handle listHandle;
    List_Elem *elem;
    ListNode *node;
    UInt32 i, value;
    Bool failed = FALSE;

    IGateProvider_Handle gateHandle;

    List_Params_init(&listParams);

    gateHandle = (IGateProvider_Handle) GateMutex_create();
    if(gateHandle == NULL) {
        Osal_printf("ListTest: GateMutex_create failed.\n");
        goto exit;
    }

    listParams.gateHandle = gateHandle;
    listHandle = List_create(&listParams);
    if(listHandle == NULL) {
        Osal_printf("ListTest: List_create failed.\n");
        goto gateExit;
    }

    node = Memory_alloc(NULL, LIST_SIZE * sizeof(ListNode), 0);
    if(node == NULL) {
        Osal_printf("ListTest: Memory_alloc failed.\n");
        goto listExit;
    }

    // Put some nodes into the list
    for(i = 0; i < LIST_SIZE; i++) {
        node[i].value = i;
        List_put(listHandle, (List_Elem *)&node[i]);
    }

    // Traverse the list
    for(i = 0, elem = List_next(listHandle, NULL);
        elem != NULL && !failed;
        i++, elem = List_next(listHandle, elem)) {
        value = ((ListNode *)elem)->value;

        // Check against expected value
        if(value != i) {
            Osal_printf("ListTest: data mismatch, expected "
                "0x%x, actual 0x%x\n", i, i, value);
            failed = TRUE;
        }
    }

    // Remove nodes
    for(i = 0; i < LIST_SIZE && !List_empty(listHandle); i++) {
        // Get first element and put it back to test List_get and List_putHead
        elem = List_get(listHandle);
        List_putHead(listHandle, elem);

        // Now remove it permanently to test List_remove
        if(elem != NULL) {
            List_remove(listHandle, elem);
        }
    }
    // Did we remove the expected number of nodes?
    if(i != LIST_SIZE)
    {
        Osal_printf("ListTest: removed %d node(s), expected %d\n",
            i, LIST_SIZE);
        failed = TRUE;
    }

    if(!List_empty(listHandle))
    {
        Osal_printf("ListTest: list not empty!\n");
        failed = TRUE;
    }

    if(failed)
        Osal_printf("ListTest: FAILED!\n");
    else
        Osal_printf("ListTest: PASSED!\n");

listExit:
    List_delete(&listHandle);
gateExit:
    GateMutex_delete((GateMutex_Handle *)&gateHandle);
exit:
    return;
}
Esempio n. 9
0
Int RcmClient_getReturnMsg_P(RcmClient_Object *obj, const UInt16 msgId,
    RcmClient_Message **returnMsg)
{
    List_Elem *elem;
    Recipient *recipient;
    RcmClient_Packet *packet;
    Bool messageDelivered;
    MessageQ_Msg msgqMsg = NULL;
    Bool messageFound = FALSE;
    Int queueLockAcquired = 0;
    Error_Block eb;
    Int rval;
    Int status = RcmClient_S_SUCCESS;


    Log_print3(Diags_ENTRY,
        "--> "FXNN": (obj=0x%x, msgId=%d, returnMsgPtr=0x%x",
        (IArg)obj, (IArg)msgId, (IArg)returnMsg);

    Error_init(&eb);
    *returnMsg = NULL;

    /* keep trying until message found */
    while (!messageFound) {

        /* acquire the mailbox lock */
        Semaphore_pend(obj->mbxLock, Semaphore_FOREVER, &eb);
        if (Error_check(&eb)) {
            /* TODO */
            goto leave;
        }

        /* search new mail list for message */
        elem = NULL;
        while ((elem = List_next(obj->newMail, elem)) != NULL) {
            packet = getPacketAddrElem(elem);
            if (msgId == packet->msgId) {
                List_remove(obj->newMail, elem);
                *returnMsg = &packet->message;
                messageFound = TRUE;
                break;
            }
        }

        if (messageFound) {
            /* release the mailbox lock */
            Semaphore_post(obj->mbxLock, &eb);
            if (Error_check(&eb)) {
                /* TODO */
            }
        }
        else {
            /* attempt the message queue lock */
            queueLockAcquired = Semaphore_pend(obj->queueLock, 0, &eb);
            if (Error_check(&eb)) {
                /* TODO */
                goto leave;
            }

            if (1 == queueLockAcquired) {
                /*
                 * mailman role
                 */

                /* deliver new mail until message found */
                while (!messageFound) {

                    /* get message from queue if available (non-blocking) */
                    if (NULL == msgqMsg) {
                        rval = MessageQ_get(obj->msgQue, &msgqMsg, 0);

                        if ((MessageQ_E_TIMEOUT != rval) && (rval < 0)) {
                            Log_error0(FXNN": lost return message");
                            status = RcmClient_E_LOSTMSG;
                            goto leave;
                        }
                        Log_print0(Diags_INFO, FXNN": return message received");
                    }

                    while (NULL != msgqMsg) {

                        /* check if message found */
                        packet = getPacketAddrMsgqMsg(msgqMsg);
                        messageFound = (msgId == packet->msgId);

                        if (messageFound) {
                            *returnMsg = &packet->message;

                            /* search wait list for new mailman */
                            elem = NULL;
                            while ((elem =
                                List_next(obj->recipients, elem)) != NULL) {
                                recipient = (Recipient *)elem;
                                if (NULL == recipient->msg) {
                                    /* signal recipient's event */
                                    SemThread_post(SemThread_handle(
                                        &recipient->event), &eb);
                                    break;
                                }
                            }

                            /* release the message queue lock */
                            Semaphore_post(obj->queueLock, &eb);
                            if (Error_check(&eb)) {
                                /* TODO */
                            }

                            /* release the mailbox lock */
                            Semaphore_post(obj->mbxLock, &eb);
                            if (Error_check(&eb)) {
                                /* TODO */
                            }

                            break;
                        }
                        else {
                            /*
                             * deliver message to mailbox
                             */

                            /* search recipient list for message owner */
                            elem = NULL;
                            messageDelivered = FALSE;
                            while ((elem =
                                List_next(obj->recipients, elem)) != NULL) {
                                recipient = (Recipient *)elem;
                                if (recipient->msgId == packet->msgId) {
                                    recipient->msg = &packet->message;
                                    /* signal the recipient's event */
                                    SemThread_post(SemThread_handle(
                                        &recipient->event), &eb);
                                    messageDelivered = TRUE;
                                    break;
                                }
                            }

                            /* add undelivered message to new mail list */
                            if (!messageDelivered) {
                                /* use the elem in the MessageQ header */
                                elem = (List_Elem *)&packet->msgqHeader;
                                List_put(obj->newMail, elem);
                            }
                        }

                        /* get next message from queue if available */
                        rval = MessageQ_get(obj->msgQue, &msgqMsg, 0);

                        if ((MessageQ_E_TIMEOUT != rval) && (rval < 0)) {
                            Log_error0(FXNN": lost return message");
                            status = RcmClient_E_LOSTMSG;
                            goto leave;
                        }
                        Log_print0(Diags_INFO, FXNN": return message received");
                    }

                    if (!messageFound) {
                        /*
                         * message queue empty
                         */

                        /* release the mailbox lock */
                        Semaphore_post(obj->mbxLock, &eb);
                        if (Error_check(&eb)) {
                            /* TODO */
                        }

                        /* get next message, this blocks the thread */
                        rval = MessageQ_get(obj->msgQue, &msgqMsg,
                            MessageQ_FOREVER);

                        if (rval < 0) {
                            Log_error0(FXNN": lost return message");
                            status = RcmClient_E_LOSTMSG;
                            goto leave;
                        }
                        Log_print0(Diags_INFO, FXNN": return message received");

                        if (msgqMsg == NULL) {
                            Log_error0(FXNN": reply message has been lost");
                            status = RcmClient_E_LOSTMSG;
                            goto leave;
                        }

                        /* acquire the mailbox lock */
                        Semaphore_pend(obj->mbxLock, Semaphore_FOREVER, &eb);
                        if (Error_check(&eb)) {
                            goto leave;  /* TODO */
                        }
                    }
                }
            }
            else {
                /* construct recipient on local stack */
                Recipient self;
                self.msgId = msgId;
                self.msg = NULL;
                SemThread_construct(&self.event, 0, NULL, &eb);
                if (Error_check(&eb)) {
                    /* TODO */
                }

                /* add recipient to wait list */
                elem = &self.elem;
                List_put(obj->recipients, elem);

                /* release the mailbox lock */
                Semaphore_post(obj->mbxLock, &eb);
                if (Error_check(&eb)) {
                    /* TODO */
                }

                /* wait on event */
                SemThread_pend(SemThread_handle(&self.event),
                    Semaphore_FOREVER, &eb);
                if (Error_check(&eb)) {
                    /* TODO */
                }

                /* acquire the mailbox lock */
                Semaphore_pend(obj->mbxLock, Semaphore_FOREVER, &eb);
                if (Error_check(&eb)) {
                    goto leave;  /* TODO */
                }

                if (NULL != self.msg) {
                    /* pickup message */
                    *returnMsg = self.msg;
                    messageFound = TRUE;
                }

                /* remove recipient from wait list */
                List_remove(obj->recipients, elem);
                SemThread_destruct(&self.event);

                /* release the mailbox lock */
                Semaphore_post(obj->mbxLock, &eb);
                if (Error_check(&eb)) {
                    /* TODO */
                }
            }
        }
    } /* while (!messageFound) */

leave:
    Log_print2(Diags_EXIT, "<-- %s: %d", (IArg)FXNN, (IArg)status);
    return(status);
}