CLDS_SORTED_LIST_GET_COUNT_RESULT clds_sorted_list_get_count()

in src/clds_sorted_list.c [1770:1817]


CLDS_SORTED_LIST_GET_COUNT_RESULT clds_sorted_list_get_count(CLDS_SORTED_LIST_HANDLE clds_sorted_list, CLDS_HAZARD_POINTERS_THREAD_HANDLE clds_hazard_pointers_thread, uint64_t* item_count)
{
    CLDS_SORTED_LIST_GET_COUNT_RESULT result;

    if (
        /*Codes_SRS_CLDS_SORTED_LIST_42_035: [ If clds_sorted_list is NULL then clds_sorted_list_get_count shall fail and return CLDS_SORTED_LIST_GET_COUNT_ERROR. ]*/
        (clds_sorted_list == NULL) ||
        /*Codes_SRS_CLDS_SORTED_LIST_42_036: [ If clds_hazard_pointers_thread is NULL then clds_sorted_list_get_count shall fail and return CLDS_SORTED_LIST_GET_COUNT_ERROR. ]*/
        (clds_hazard_pointers_thread == NULL) ||
        /*Codes_SRS_CLDS_SORTED_LIST_42_037: [ If item_count is NULL then clds_sorted_list_get_count shall fail and return CLDS_SORTED_LIST_GET_COUNT_ERROR. ]*/
        (item_count == NULL)
        )
    {
        /*Codes_SRS_CLDS_SORTED_LIST_42_038: [ If the counter to lock the list for writes is 0 then clds_sorted_list_get_count shall fail and return CLDS_SORTED_LIST_GET_COUNT_NOT_LOCKED. ]*/
        LogError("Invalid arguments: CLDS_SORTED_LIST_HANDLE clds_sorted_list=%p, CLDS_HAZARD_POINTERS_THREAD_HANDLE clds_hazard_pointers_thread=%p, uint64_t* item_count=%p",
            clds_sorted_list, clds_hazard_pointers_thread, item_count);
        result = CLDS_SORTED_LIST_GET_COUNT_ERROR;
    }
    else
    {
        if (interlocked_add(&clds_sorted_list->locked_for_write, 0) == 0)
        {
            /*Codes_SRS_CLDS_SORTED_LIST_42_038: [ If the counter to lock the list for writes is 0 then clds_sorted_list_get_count shall fail and return CLDS_SORTED_LIST_GET_COUNT_NOT_LOCKED. ]*/
            LogError("Must lock the list before getting the count of items");
            result = CLDS_SORTED_LIST_GET_COUNT_NOT_LOCKED;
        }
        else
        {
            /*Codes_SRS_CLDS_SORTED_LIST_42_039: [ clds_sorted_list_get_count shall iterate over the items in the list and count them in item_count. ]*/
            uint64_t count = 0;
            CLDS_SORTED_LIST_ITEM* current_item = interlocked_compare_exchange_pointer((void* volatile_atomic*)&clds_sorted_list->head, NULL, NULL);

            while (current_item != NULL)
            {
                count++;
                CLDS_SORTED_LIST_ITEM* next_item = interlocked_compare_exchange_pointer((void* volatile_atomic*)&current_item->next, NULL, NULL);
                current_item = next_item;
            }

            *item_count = count;

            /*Codes_SRS_CLDS_SORTED_LIST_42_040: [ clds_sorted_list_get_count shall succeed and return CLDS_SORTED_LIST_GET_COUNT_OK. ]*/
            result = CLDS_SORTED_LIST_GET_COUNT_OK;
        }
    }

    return result;
}