Ignore:
Timestamp:
Nov 6, 2019 6:17:53 AM (4 years ago)
Author:
riza
Message:

Close #2249: Use sorted linked list for timer implementation.

File:
1 edited

Legend:

Unmodified
Added
Removed
  • pjproject/trunk/pjlib/src/pjlib-test/timer.c

    r6059 r6099  
    208208 */ 
    209209#define RANDOMIZED_TEST 1 
    210 #define SIMULATE_CRASH  PJ_TIMER_HEAP_USE_COPY 
     210#define SIMULATE_CRASH  PJ_TIMER_USE_COPY 
    211211 
    212212#if RANDOMIZED_TEST 
     
    231231#define ST_ENTRY_GROUP_LOCK_COUNT   1 
    232232 
     233#define BT_ENTRY_COUNT 100000 
     234#define BT_ENTRY_SHOW_START 100 
     235#define BT_ENTRY_SHOW_MULT 10 
     236#define BT_REPEAT_RANDOM_TEST 4 
     237#define BT_REPEAT_INC_TEST 4 
    233238 
    234239struct thread_param 
     
    269274static void dummy_callback(pj_timer_heap_t *ht, pj_timer_entry *e) 
    270275{ 
     276    PJ_UNUSED_ARG(ht); 
    271277    PJ_LOG(4,("test", "dummy callback called %p %p", e, e->user_data)); 
    272278} 
     
    747753} 
    748754 
     755static int get_random_delay() 
     756{ 
     757    return pj_rand() % BT_ENTRY_COUNT; 
     758} 
     759 
     760static int get_next_delay(int delay) 
     761{ 
     762    return ++delay; 
     763} 
     764 
     765typedef enum BENCH_TEST_TYPE { 
     766    RANDOM_SCH = 0, 
     767    RANDOM_CAN = 1, 
     768    INCREMENT_SCH = 2, 
     769    INCREMENT_CAN = 3 
     770} BENCH_TEST_TYPE; 
     771 
     772static char *get_test_name(BENCH_TEST_TYPE test_type) { 
     773    switch (test_type) { 
     774    case RANDOM_SCH: 
     775    case INCREMENT_SCH: 
     776        return "schedule"; 
     777    case RANDOM_CAN: 
     778    case INCREMENT_CAN: 
     779        return "cancel"; 
     780    } 
     781    return "undefined"; 
     782} 
     783 
     784static void *get_format_num(unsigned n, char *out) 
     785{ 
     786    int c; 
     787    char buf[64]; 
     788    char *p; 
     789 
     790    pj_ansi_snprintf(buf, 64, "%d", n); 
     791    c = 2 - pj_ansi_strlen(buf) % 3; 
     792    for (p = buf; *p != 0; ++p) { 
     793       *out++ = *p; 
     794       if (c == 1) { 
     795           *out++ = ','; 
     796       } 
     797       c = (c + 1) % 3; 
     798    } 
     799    *--out = 0; 
     800    return out; 
     801} 
     802 
     803static void print_bench(BENCH_TEST_TYPE test_type, pj_timestamp time_freq, 
     804                        pj_timestamp time_start, int start_idx, int end_idx) 
     805{ 
     806    char start_idx_str[64]; 
     807    char end_idx_str[64]; 
     808    char num_req_str[64]; 
     809    unsigned num_req; 
     810    pj_timestamp t2; 
     811 
     812    pj_get_timestamp(&t2); 
     813    pj_sub_timestamp(&t2, &time_start); 
     814 
     815    num_req = (unsigned)(time_freq.u64 * (end_idx-start_idx) / t2.u64); 
     816    if (test_type == RANDOM_CAN || test_type == INCREMENT_CAN) { 
     817        start_idx = BT_ENTRY_COUNT - start_idx; 
     818        end_idx = BT_ENTRY_COUNT - end_idx; 
     819    } 
     820    get_format_num(start_idx, start_idx_str); 
     821    get_format_num(end_idx, end_idx_str); 
     822    get_format_num(num_req, num_req_str); 
     823 
     824    PJ_LOG(3, (THIS_FILE, "    Entries %s-%s: %s %s ent/sec", 
     825               start_idx_str, end_idx_str, get_test_name(test_type), 
     826               num_req_str)); 
     827} 
     828 
     829static int bench_test(pj_timer_heap_t *timer, 
     830                      pj_timer_entry *entries, 
     831                      pj_timestamp freq, 
     832                      BENCH_TEST_TYPE test_type) 
     833{ 
     834    pj_timestamp t1, t2; 
     835    unsigned mult = BT_ENTRY_SHOW_START; 
     836    int i, j; 
     837 
     838    pj_get_timestamp(&t1); 
     839    t2.u64 = 0; 
     840    /*Schedule random entry.*/ 
     841    for (i=0, j=0; j < BT_ENTRY_COUNT; ++j) { 
     842        pj_time_val delay = { 0 }; 
     843        pj_status_t status; 
     844 
     845        switch (test_type) { 
     846        case RANDOM_SCH: 
     847            delay.msec = get_random_delay(); 
     848            break; 
     849        case INCREMENT_SCH: 
     850            delay.msec = get_next_delay(delay.msec); 
     851            break; 
     852        } 
     853 
     854        if (test_type == RANDOM_SCH || test_type == INCREMENT_SCH) { 
     855            pj_timer_entry_init(&entries[j], 0, NULL, &dummy_callback); 
     856 
     857            status = pj_timer_heap_schedule(timer, &entries[j], &delay); 
     858            if (status != PJ_SUCCESS) { 
     859                app_perror("...error: unable to schedule timer entry", status); 
     860                return -50; 
     861            } 
     862        } else if (test_type == RANDOM_CAN || test_type == INCREMENT_CAN) { 
     863            unsigned num_ent = pj_timer_heap_cancel(timer, &entries[j]); 
     864            if (num_ent == 0) { 
     865                PJ_LOG(3, ("test", "...error: unable to cancel timer entry")); 
     866                return -60; 
     867            } 
     868        } else { 
     869            return -70; 
     870        } 
     871 
     872        if (j && (j % mult) == 0) { 
     873            print_bench(test_type, freq, t1, i, j); 
     874 
     875            i = j+1; 
     876            pj_get_timestamp(&t1); 
     877            mult *= BT_ENTRY_SHOW_MULT; 
     878        } 
     879    } 
     880    if (j > 0 && ((j-1) % mult != 0)) { 
     881        print_bench(test_type, freq, t1, i, j); 
     882    } 
     883    return 0; 
     884} 
     885 
     886static int timer_bench_test(void) 
     887{ 
     888    pj_pool_t *pool = NULL; 
     889    pj_timer_heap_t *timer = NULL; 
     890    pj_status_t status; 
     891    int err=0; 
     892    pj_timer_entry *entries = NULL; 
     893    pj_timestamp freq; 
     894    int i; 
     895 
     896    PJ_LOG(3,("test", "...Benchmark test")); 
     897 
     898    status = pj_get_timestamp_freq(&freq); 
     899    if (status != PJ_SUCCESS) { 
     900        PJ_LOG(3,("test", "...error: unable to get timestamp freq")); 
     901        err = -10; 
     902        goto on_return; 
     903    } 
     904 
     905    pool = pj_pool_create( mem, NULL, 128, 128, NULL); 
     906    if (!pool) { 
     907        PJ_LOG(3,("test", "...error: unable to create pool")); 
     908        err = -20; 
     909        goto on_return; 
     910    } 
     911 
     912    /* Create timer heap.*/ 
     913    status = pj_timer_heap_create(pool, BT_ENTRY_COUNT/64, &timer); 
     914    if (status != PJ_SUCCESS) { 
     915        app_perror("...error: unable to create timer heap", status); 
     916        err = -30; 
     917        goto on_return; 
     918    } 
     919 
     920    /* Create and schedule timer entries */ 
     921    entries = (pj_timer_entry*)pj_pool_calloc(pool, BT_ENTRY_COUNT, 
     922                                              sizeof(*entries)); 
     923    if (!entries) { 
     924        err = -40; 
     925        goto on_return; 
     926    } 
     927 
     928    PJ_LOG(3,("test", "....random scheduling/cancelling test..")); 
     929    for (i = 0; i < BT_REPEAT_RANDOM_TEST; ++i) { 
     930        PJ_LOG(3,("test", "    test %d of %d..", i+1, BT_REPEAT_RANDOM_TEST)); 
     931        err = bench_test(timer, entries, freq, RANDOM_SCH); 
     932        if (err < 0) 
     933            goto on_return; 
     934 
     935        err = bench_test(timer, entries, freq, RANDOM_CAN); 
     936        if (err < 0) 
     937            goto on_return; 
     938    } 
     939 
     940    PJ_LOG(3,("test", "....increment scheduling/cancelling test..")); 
     941    for (i = 0; i < BT_REPEAT_INC_TEST; ++i) { 
     942        PJ_LOG(3,("test", "    test %d of %d..", i+1, BT_REPEAT_INC_TEST)); 
     943        err = bench_test(timer, entries, freq, INCREMENT_SCH); 
     944        if (err < 0) 
     945            goto on_return; 
     946 
     947        err = bench_test(timer, entries, freq, INCREMENT_CAN); 
     948        if (err < 0) 
     949            goto on_return; 
     950    } 
     951 on_return: 
     952    PJ_LOG(3,("test", "...Cleaning up resources")); 
     953    if (pool) 
     954        pj_pool_safe_release(&pool); 
     955    return err; 
     956} 
     957 
    749958int timer_test() 
    750959{ 
     
    756965 
    757966    rc = timer_stress_test(); 
     967    if (rc != 0) 
     968        return rc; 
     969 
     970    rc = timer_bench_test(); 
    758971    if (rc != 0) 
    759972        return rc; 
Note: See TracChangeset for help on using the changeset viewer.