1 /** 2 * @file lv_tick.c 3 * Provide access to the system tick with 1 millisecond resolution 4 */ 5 6 /********************* 7 * INCLUDES 8 *********************/ 9 #include "lv_tick_private.h" 10 #include "../misc/lv_types.h" 11 #include "../core/lv_global.h" 12 13 /********************* 14 * DEFINES 15 *********************/ 16 #define state LV_GLOBAL_DEFAULT()->tick_state 17 18 /********************** 19 * TYPEDEFS 20 **********************/ 21 22 /********************** 23 * STATIC PROTOTYPES 24 **********************/ 25 26 /********************** 27 * STATIC VARIABLES 28 **********************/ 29 30 /********************** 31 * MACROS 32 **********************/ 33 34 /********************** 35 * GLOBAL FUNCTIONS 36 **********************/ 37 lv_tick_inc(uint32_t tick_period)38LV_ATTRIBUTE_TICK_INC void lv_tick_inc(uint32_t tick_period) 39 { 40 lv_tick_state_t * state_p = &state; 41 42 state_p->sys_irq_flag = 0; 43 state_p->sys_time += tick_period; 44 } 45 lv_tick_get(void)46uint32_t lv_tick_get(void) 47 { 48 lv_tick_state_t * state_p = &state; 49 50 if(state_p->tick_get_cb) 51 return state_p->tick_get_cb(); 52 53 /*If `lv_tick_inc` is called from an interrupt while `sys_time` is read 54 *the result might be corrupted. 55 *This loop detects if `lv_tick_inc` was called while reading `sys_time`. 56 *If `tick_irq_flag` was cleared in `lv_tick_inc` try to read again 57 *until `tick_irq_flag` remains `1`.*/ 58 uint32_t result; 59 do { 60 state_p->sys_irq_flag = 1; 61 result = state_p->sys_time; 62 } while(!state_p->sys_irq_flag); /*Continue until see a non interrupted cycle*/ 63 64 return result; 65 } 66 lv_tick_elaps(uint32_t prev_tick)67uint32_t lv_tick_elaps(uint32_t prev_tick) 68 { 69 uint32_t act_time = lv_tick_get(); 70 71 /*If there is no overflow in sys_time simple subtract*/ 72 if(act_time >= prev_tick) { 73 prev_tick = act_time - prev_tick; 74 } 75 else { 76 prev_tick = UINT32_MAX - prev_tick + 1; 77 prev_tick += act_time; 78 } 79 80 return prev_tick; 81 } 82 lv_delay_ms(uint32_t ms)83void lv_delay_ms(uint32_t ms) 84 { 85 if(state.delay_cb) { 86 state.delay_cb(ms); 87 } 88 else { 89 uint32_t t = lv_tick_get(); 90 while(lv_tick_elaps(t) < ms) { 91 /*Do something to no call `lv_tick_elaps` too often as it might interfere with interrupts*/ 92 volatile uint32_t i; 93 volatile uint32_t x = ms; 94 for(i = 0; i < 100; i++) { 95 x = x * 3; 96 } 97 } 98 } 99 } 100 lv_tick_set_cb(lv_tick_get_cb_t cb)101void lv_tick_set_cb(lv_tick_get_cb_t cb) 102 { 103 state.tick_get_cb = cb; 104 } 105 lv_delay_set_cb(lv_delay_cb_t cb)106void lv_delay_set_cb(lv_delay_cb_t cb) 107 { 108 state.delay_cb = cb; 109 } 110 111 /********************** 112 * STATIC FUNCTIONS 113 **********************/ 114