コード例 #1
0
ファイル: aj_wsl_wmi.c プロジェクト: durake/core-ajtcl
/*
 * This function just returns the work item. If there is data inside that you want
 * you have to unmarshal it after you receive the work item.
 */
AJ_Status AJ_WSL_WMI_WaitForWorkItem(uint32_t socket, uint8_t command, wsl_work_item** item, uint32_t timeout)
{
    AJ_Status status;
    AJ_Time timer;
    AJ_InitTimer(&timer);
//    AJ_AlwaysPrintf(("WaitForWorkItem: %x\n", command));
    //wsl_work_item* item;
    status = AJ_QueuePull(AJ_WSL_SOCKET_CONTEXT[socket].workRxQueue, item, timeout);
    timeout -= AJ_GetElapsedTime(&timer, TRUE);
    if ((status == AJ_OK) && item && *item) {
        if ((status == AJ_OK) && ((*item)->itemType == WSL_NET_INTERUPT)) {
            // We don't care about the interrupted signal for any calls using this function
            AJ_WSL_WMI_FreeWorkItem((*item));
            status = AJ_QueuePull(AJ_WSL_SOCKET_CONTEXT[socket].workRxQueue, item, timeout);
        }
        if ((status == AJ_OK) && ((*item)->itemType == command)) {
            AJ_InfoPrintf(("AJ_WSL_WMI_WaitForWorkItem(): Received work item %s\n", WSL_WorkItemText(command)));
            return AJ_OK;
        } else if ((status == AJ_OK) && ((*item)->itemType == WSL_NET_DISCONNECT)) {
            AJ_InfoPrintf(("Got disconnect while waiting for %s\n", WSL_WorkItemText(command)));
            // Clean up the network queues
            int i;
            for (i = 0; i < AJ_WSL_SOCKET_MAX; i++) {
                wsl_work_item* clear;
                AJ_WSL_SOCKET_CONTEXT[i].valid = FALSE;
                // Removed any stashed data
                AJ_BufListFree(AJ_WSL_SOCKET_CONTEXT[i].stashedRxList, 1);
                // Reallocate a new stash
                AJ_WSL_SOCKET_CONTEXT[i].stashedRxList = AJ_BufListCreate();
                // Reset the queue, any work items are now invalid since the socket was closed
                while (AJ_QueuePull(AJ_WSL_SOCKET_CONTEXT[i].workRxQueue, &clear, 0) == AJ_OK) {
                    AJ_WSL_WMI_FreeWorkItem(clear);
                }
                while (AJ_QueuePull(AJ_WSL_SOCKET_CONTEXT[i].workTxQueue, &clear, 0) == AJ_OK) {
                    AJ_WSL_WMI_FreeWorkItem(clear);
                }
                AJ_QueueReset(AJ_WSL_SOCKET_CONTEXT[i].workRxQueue);
                AJ_QueueReset(AJ_WSL_SOCKET_CONTEXT[i].workTxQueue);
            }
            AJ_WSL_WMI_FreeWorkItem((*item));
            return AJ_ERR_LINK_DEAD;
        } else if ((status == AJ_OK) && ((*item)->itemType == WSL_NET_DATA_RX)) {
            // If we got data we want to save it and not throw it away, its still not what we
            // wanted so we can free the work item as it wont be needed at a higher level
            AJ_InfoPrintf(("Got data while waiting for %s\n", WSL_WorkItemText(command)));
            if ((*item)->node->length) {
                AJ_BufNode* new_node = AJ_BufNodeCreateAndTakeOwnership((*item)->node);
                AJ_BufListPushTail(AJ_WSL_SOCKET_CONTEXT[socket].stashedRxList, new_node);
                AJ_WSL_WMI_FreeWorkItem((*item));
                return AJ_ERR_NULL;
            }
        } else {
            AJ_WarnPrintf(("AJ_WSL_WMI_WaitForWorkItem(): Received incorrect work item %s, wanted %s\n", WSL_WorkItemText((*item)->itemType), WSL_WorkItemText(command)));
            // Wrong work item, but return NULL because we can free the item internally
            AJ_WSL_WMI_FreeWorkItem((*item));
            return AJ_ERR_NULL;
        }
    }
    return AJ_ERR_NULL;
}
コード例 #2
0
ファイル: aj_wsl_net.c プロジェクト: fonlabs/ajtcl
/*
 *  create the WMI request to bind a socket on the target device to an address and port
 */
int16_t AJ_WSL_NET_socket_recv(AJ_WSL_SOCKNUM sock, uint8_t* buffer, uint32_t sizeBuffer, uint32_t timeout)
{
//    AJ_InfoPrintf(("AJ_WSL_NET_socket_recv()\n"));
    int16_t ret = -1;
    uint32_t rx = sizeBuffer;
    uint32_t stash = 0;
    // read from stash first.
    uint16_t stashLength;

    if (sock >= AJ_WSL_SOCKET_MAX) {
        // tried to get data from an invalid socket, return an error
        return ret;
    }
    if (AJ_WSL_SOCKET_CONTEXT[sock].valid == FALSE) {
        // tried to get data from an invalid socket, return the data read from the stash
        AJ_BufListFree(AJ_WSL_SOCKET_CONTEXT[sock].stashedRxList, 1);
        AJ_WSL_SOCKET_CONTEXT[sock].stashedRxList = AJ_BufListCreate();
        //flush the queue
        AJ_QueueReset(AJ_WSL_SOCKET_CONTEXT[sock].workRxQueue);
        return ret;
    }

    if (AJ_WSL_SOCKET_CONTEXT[sock].stashedRxList) {
        stashLength = AJ_BufListLengthOnWire(AJ_WSL_SOCKET_CONTEXT[sock].stashedRxList);
        if (stashLength != 0) {
            stash = min(rx, stashLength);
            AJ_BufListCopyBytes(AJ_WSL_SOCKET_CONTEXT[sock].stashedRxList, stash, buffer);
            AJ_BufListPullBytes(AJ_WSL_SOCKET_CONTEXT[sock].stashedRxList, stash); // shift left-overs toward the start.
            ret = stash;
            sizeBuffer -= stash;
        }
    }


    // wait until there is data
    if (sizeBuffer) {
        wsl_work_item* item = NULL;
        AJ_Status status;

        // the stash was depleted and you want more data
        if (AJ_WSL_SOCKET_CONTEXT[sock].valid == FALSE) {
            // tried to get data from an invalid socket, return the data read from the stash
            return ret;
        }


        status = AJ_QueuePull(AJ_WSL_SOCKET_CONTEXT[sock].workRxQueue, &item, timeout);
        if (item) {
            if (item->itemType == WSL_NET_INTERUPT) {
                // At this point we dont care about the interrupted signal but we are expecting a RX packet
                // so we need to pull the next item off the queue
                AJ_WSL_WMI_FreeWorkItem(item);
                status = AJ_QueuePull(AJ_WSL_SOCKET_CONTEXT[sock].workRxQueue, &item, timeout);
            }
            if ((status == AJ_OK) && (item->itemType == WSL_NET_DISCONNECT)) {
                AJ_InfoPrintf(("Disconnect received\n"));
                // Clean up the network queues
                int i;
                for (i = 0; i < AJ_WSL_SOCKET_MAX; i++) {
                    AJ_WSL_SOCKET_CONTEXT[i].valid = FALSE;
                    // Removed any stashed data
                    AJ_BufListFree(AJ_WSL_SOCKET_CONTEXT[i].stashedRxList, 1);
                    // Reallocate a new stash
                    AJ_WSL_SOCKET_CONTEXT[i].stashedRxList = AJ_BufListCreate();
                    // Reset the queue, any work items are now invalid since the socket was closed
                    AJ_QueueReset(AJ_WSL_SOCKET_CONTEXT[i].workRxQueue);
                    AJ_QueueReset(AJ_WSL_SOCKET_CONTEXT[i].workTxQueue);
                }
                ret = -1;
            } else if ((status == AJ_OK) && (item->itemType == WSL_NET_CLOSE || item->itemType == AJ_WSL_WORKITEM(AJ_WSL_WORKITEM_SOCKET, WSL_SOCK_CLOSE))) {
                // Pull the close work item off the queue
                AJ_QueuePull(AJ_WSL_SOCKET_CONTEXT[sock].workRxQueue, &item, 0);
                // Socket was closed so tear down the connections
                AJ_WSL_SOCKET_CONTEXT[sock].valid = FALSE;
                // Removed any stashed data
                AJ_BufListFree(AJ_WSL_SOCKET_CONTEXT[sock].stashedRxList, 1);
                // Reallocate a new stash
                AJ_WSL_SOCKET_CONTEXT[sock].stashedRxList = AJ_BufListCreate();
                // Reset the queue, any work items are now invalid since the socket was closed
                AJ_QueueReset(AJ_WSL_SOCKET_CONTEXT[sock].workRxQueue);
                AJ_QueueReset(AJ_WSL_SOCKET_CONTEXT[sock].workTxQueue);
                ret = -1;
            } else if ((status == AJ_OK) && (item->itemType == WSL_NET_DATA_RX)) {

                //AJ_InfoPrintf(("=====DATA RX ITEM RECEIVED=====\n"));
                //AJ_DumpBytes("DATA RX ITEM", item->node->buffer, item->size);
                rx = min(sizeBuffer, item->size);
                memcpy(buffer + stash, item->node->buffer, rx);
                AJ_BufNodePullBytes(item->node, rx);
                // check node: if not empty assign to stash.
                if (item->node->length) {
                    AJ_BufListPushTail(AJ_WSL_SOCKET_CONTEXT[sock].stashedRxList, item->node);
                    item->node = NULL;
                }
                ret = rx + stash;
            } else {
                AJ_InfoPrintf(("AJ_WSL_NET_socket_recv(): BAD WORK ITEM RECEIVED\n"));
            }
            AJ_WSL_WMI_FreeWorkItem(item);
        } else {
            ret = 0;
            AJ_InfoPrintf(("socket_recv timed out\n"));
        }
    }

    return ret;
}
コード例 #3
0
ファイル: aj_wsl_net.c プロジェクト: fonlabs/ajtcl
/*
 * Poll over a socket until there is data ready or till a timeout
 *
 * Returns -2 on timeout
 *         -1 on interrupted
 *          1 on success
 *          0 on close
 *
 */
int16_t AJ_WSL_NET_socket_select(AJ_WSL_SOCKNUM sock, uint32_t timeout)
{
    AJ_Time timer;
    wsl_work_item* peek;
    AJ_Status status;
    int16_t ret = 0;
    // Check if the socket is valid
    if (sock >= AJ_WSL_SOCKET_MAX) {
        // tried to get data from an invalid socket, return an error
        return ret;
    }
    if (AJ_WSL_SOCKET_CONTEXT[sock].valid == FALSE) {
        // tried to get data from an invalid socket, return the data read from the stash
        AJ_BufListFree(AJ_WSL_SOCKET_CONTEXT[sock].stashedRxList, 1);
        AJ_WSL_SOCKET_CONTEXT[sock].stashedRxList = AJ_BufListCreate();
        //flush the queue
        return ret;
    }
    AJ_InitTimer(&timer);
    // There are 5 conditions that we need to check for
    // 1. If we got an interrupted work item
    // 2. If there is data in the RX stash
    // 3. If there is a RX work item in the queue
    // 4. If there is a socket close work item in the queue
    // 5. If the timeout has expired
    while (1) {
        status = AJ_QueuePeek(AJ_WSL_SOCKET_CONTEXT[sock].workRxQueue, &peek);
        //AJ_AlwaysPrintf(("Item type = %u\n", peek->itemType));
        if ((status == AJ_OK) && (peek->itemType == WSL_NET_INTERUPT)) {
            // Pull the interrupted item off because we dont need it anymore
            AJ_QueuePull(AJ_WSL_SOCKET_CONTEXT[sock].workRxQueue, &peek, 0);
            AJ_WSL_WMI_FreeWorkItem(peek);
            ret = -1;
            break;
        } else if (AJ_BufListLengthOnWire(AJ_WSL_SOCKET_CONTEXT[sock].stashedRxList) > 0) {
            ret = 1;
            break;
        } else if ((status == AJ_OK) && (peek->itemType == WSL_NET_DATA_RX)) {
            ret = 1;
            break;
        } else if ((status == AJ_OK) && (peek->itemType == WSL_NET_CLOSE ||
                                         peek->itemType == WSL_NET_DISCONNECT ||
                                         peek->itemType == AJ_WSL_WORKITEM(AJ_WSL_WORKITEM_SOCKET, WSL_SOCK_CLOSE))) {
            // Pull the close work item off the queue
            AJ_QueuePull(AJ_WSL_SOCKET_CONTEXT[sock].workRxQueue, &peek, 0);
            // Socket was closed so tear down the connections
            AJ_WSL_SOCKET_CONTEXT[sock].valid = FALSE;
            // Removed any stashed data
            AJ_BufListFree(AJ_WSL_SOCKET_CONTEXT[sock].stashedRxList, 1);
            // Reallocate a new stash
            AJ_WSL_SOCKET_CONTEXT[sock].stashedRxList = AJ_BufListCreate();
            // Reset the queue, any work items are now invalid since the socket was closed
            AJ_QueueReset(AJ_WSL_SOCKET_CONTEXT[sock].workRxQueue);
            AJ_QueueReset(AJ_WSL_SOCKET_CONTEXT[sock].workTxQueue);
            AJ_WSL_WMI_FreeWorkItem(peek);
            ret = 0;
            break;
        } else if (AJ_GetElapsedTime(&timer, TRUE) >= timeout) {
            ret = -2;
            break;
        }
    }
    return ret;
}