void lp_ticker_init() { core_util_critical_section_enter(); if (!rtc_inited) { CMU_ClockEnable(cmuClock_RTC, true); /* Initialize RTC */ RTC_Init_TypeDef init = RTC_INIT_DEFAULT; init.enable = 1; /* Don't use compare register 0 as top value */ init.comp0Top = 0; /* Initialize */ RTC_Init(&init); RTC_CounterSet(20); /* Enable Interrupt from RTC */ RTC_IntDisable(RTC_IF_COMP0); RTC_IntClear(RTC_IF_COMP0); NVIC_SetVector(RTC_IRQn, (uint32_t)RTC_IRQHandler); NVIC_EnableIRQ(RTC_IRQn); rtc_inited = true; } else { /* Cancel current interrupt by virtue of calling init again */ RTC_IntDisable(RTC_IF_COMP0); RTC_IntClear(RTC_IF_COMP0); } core_util_critical_section_exit(); }
void sleep_manager_sleep_auto(void) { #ifdef MBED_SLEEP_TRACING_ENABLED sleep_tracker_print_stats(); #endif core_util_critical_section_enter(); us_timestamp_t start = read_us(); bool deep = false; // debug profile should keep debuggers attached, no deep sleep allowed #ifdef MBED_DEBUG hal_sleep(); #else if (sleep_manager_can_deep_sleep()) { deep = true; hal_deepsleep(); } else { hal_sleep(); } #endif us_timestamp_t end = read_us(); if (true == deep) { deep_sleep_time += end - start; } else { sleep_time += end - start; } core_util_critical_section_exit(); }
void Ticker::setup(timestamp_t t) { core_util_critical_section_enter(); remove(); _delay = t; insert(_delay + ticker_read(_ticker_data)); core_util_critical_section_exit(); }
int cy_reserve_crypto(cy_en_crypto_submodule_t module_num) { int result = (-1); if (module_num < NUM_CRYPTO_HW) { core_util_critical_section_enter(); if (cy_crypto_reserved_status() == 0) { /* Enable Crypto IP on demand */ Cy_Crypto_Core_Enable(CRYPTO); } if (module_num == CY_CRYPTO_COMMON_HW) { if (crypto_reservations[module_num] != 1) { crypto_reservations[module_num] = 1; result = 0; } } else { crypto_reservations[module_num] = 1; result = 0; } core_util_critical_section_exit(); } return result; }
int SPI::queue_transfer(const void *tx_buffer, int tx_length, void *rx_buffer, int rx_length, unsigned char bit_width, const event_callback_t& callback, int event) { #if TRANSACTION_QUEUE_SIZE_SPI transaction_t t; t.tx_buffer = const_cast<void *>(tx_buffer); t.tx_length = tx_length; t.rx_buffer = rx_buffer; t.rx_length = rx_length; t.event = event; t.callback = callback; t.width = bit_width; Transaction<SPI> transaction(this, t); if (_transaction_buffer.full()) { return -1; // the buffer is full } else { core_util_critical_section_enter(); _transaction_buffer.push(transaction); if (!spi_active(&_spi)) { dequeue_transaction(); } core_util_critical_section_exit(); return 0; } #else return -1; #endif }
void mbed_error_vfprintf(const char * format, va_list arg) { #if DEVICE_SERIAL #define ERROR_BUF_SIZE (128) core_util_critical_section_enter(); char buffer[ERROR_BUF_SIZE]; int size = vsnprintf(buffer, ERROR_BUF_SIZE, format, arg); if (size > 0) { if (!stdio_uart_inited) { serial_init(&stdio_uart, STDIO_UART_TX, STDIO_UART_RX); } #if MBED_CONF_PLATFORM_STDIO_CONVERT_NEWLINES char stdio_out_prev = '\0'; for (int i = 0; i < size; i++) { if (buffer[i] == '\n' && stdio_out_prev != '\r') { serial_putc(&stdio_uart, '\r'); } serial_putc(&stdio_uart, buffer[i]); stdio_out_prev = buffer[i]; } #else for (int i = 0; i < size; i++) { serial_putc(&stdio_uart, buffer[i]); } #endif } core_util_critical_section_exit(); #endif }
timestamp_t lp_ticker_read() { if (! lp_ticker_inited) { lp_ticker_init(); } TIMER_T * timer2_base = (TIMER_T *) NU_MODBASE(timer2_modinit.modname); do { uint64_t major_minor_clks; uint32_t minor_clks; // NOTE: As TIMER_CNT = TIMER_CMP and counter_major has increased by one, TIMER_CNT doesn't change to 0 for one tick time. // NOTE: As TIMER_CNT = TIMER_CMP or TIMER_CNT = 0, counter_major (ISR) may not sync with TIMER_CNT. So skip and fetch stable one at the cost of 1 clock delay on this read. do { core_util_critical_section_enter(); // NOTE: Order of reading minor_us/carry here is significant. minor_clks = TIMER_GetCounter(timer2_base); uint32_t carry = (timer2_base->INTSTS & TIMER_INTSTS_TIF_Msk) ? 1 : 0; // When TIMER_CNT approaches TIMER_CMP and will wrap soon, we may get carry but TIMER_CNT not wrapped. Handle carefully carry == 1 && TIMER_CNT is near TIMER_CMP. if (carry && minor_clks > (TMR2_CLK_PER_TMR2_INT / 2)) { major_minor_clks = (counter_major + 1) * TMR2_CLK_PER_TMR2_INT; } else { major_minor_clks = (counter_major + carry) * TMR2_CLK_PER_TMR2_INT + minor_clks; } core_util_critical_section_exit(); } while (minor_clks == 0 || minor_clks == TMR2_CLK_PER_TMR2_INT); // Add power-down compensation return ((uint64_t) major_minor_clks * US_PER_SEC / TMR2_CLK_PER_SEC / US_PER_TICK); } while (0); }
void ticker_insert_event(const ticker_data_t *const data, ticker_event_t *obj, timestamp_t timestamp, uint32_t id) { /* disable interrupts for the duration of the function */ core_util_critical_section_enter(); // initialise our data obj->timestamp = timestamp; obj->id = id; /* Go through the list until we either reach the end, or find an element this should come before (which is possibly the head). */ ticker_event_t *prev = NULL, *p = data->queue->head; while (p != NULL) { /* check if we come before p */ if ((int)(timestamp - p->timestamp) < 0) { break; } /* go to the next element */ prev = p; p = p->next; } /* if prev is NULL we're at the head */ if (prev == NULL) { data->queue->head = obj; data->interface->set_interrupt(timestamp); } else { prev->next = obj; } /* if we're at the end p will be NULL, which is correct */ obj->next = p; core_util_critical_section_exit(); }
void ticker_remove_event(const ticker_data_t *const data, ticker_event_t *obj) { core_util_critical_section_enter(); // remove this object from the list if (data->queue->head == obj) { // first in the list, so just drop me data->queue->head = obj->next; if (data->queue->head == NULL) { data->interface->disable_interrupt(); } else { data->interface->set_interrupt(data->queue->head->timestamp); } } else { // find the object before me, then drop me ticker_event_t* p = data->queue->head; while (p != NULL) { if (p->next == obj) { p->next = obj->next; break; } p = p->next; } } core_util_critical_section_exit(); }
uint32_t cy_clk_allocate_divider(cy_en_divider_types_t div_type) { uint32_t divider = CY_INVALID_DIVIDER; divider_alloc_t *p_alloc = ÷r_allocations[div_type]; MBED_ASSERT(div_type < CY_NUM_DIVIDER_TYPES); core_util_critical_section_enter(); MBED_ASSERT(p_alloc->current_index < p_alloc->max_index); for ( uint32_t first_index = p_alloc->current_index; CY_INVALID_DIVIDER == (divider = cy_clk_reserve_divider(div_type, p_alloc->current_index)); ++p_alloc->current_index) { if (p_alloc->current_index > p_alloc->max_index) { p_alloc->current_index = 0; } if (p_alloc->current_index == first_index) { break; } } core_util_critical_section_exit(); return divider; }
clock_t clock() { core_util_critical_section_enter(); clock_t t = us_ticker_read(); t /= 1000000 / CLOCKS_PER_SEC; // convert to processor time core_util_critical_section_exit(); return t; }
void attach_rtc(time_t (*read_rtc)(void), void (*write_rtc)(time_t), void (*init_rtc)(void), int (*isenabled_rtc)(void)) { core_util_critical_section_enter(); _rtc_read = read_rtc; _rtc_write = write_rtc; _rtc_init = init_rtc; _rtc_isenabled = isenabled_rtc; core_util_critical_section_exit(); }
void lp_ticker_free() { if(rtc_reserved) { core_util_critical_section_enter(); rtc_free_real(RTC_INIT_LPTIMER); rtc_reserved = 0; core_util_critical_section_exit(); } }
uint32_t core_util_atomic_decr_u32(uint32_t *valuePtr, uint32_t delta) { uint32_t newValue; core_util_critical_section_enter(); newValue = *valuePtr - delta; *valuePtr = newValue; core_util_critical_section_exit(); return newValue; }
uint16_t core_util_atomic_incr_u16(uint16_t *valuePtr, uint16_t delta) { uint16_t newValue; core_util_critical_section_enter(); newValue = *valuePtr + delta; *valuePtr = newValue; core_util_critical_section_exit(); return newValue; }
us_timestamp_t Timer::slicetime() { us_timestamp_t ret = 0; core_util_critical_section_enter(); if (_running) { ret = ticker_read_us(_ticker_data) - _start; } core_util_critical_section_exit(); return ret; }
void nRF5xn::processEvents() { core_util_critical_section_enter(); while (isEventsSignaled) { isEventsSignaled = false; core_util_critical_section_exit(); #if NRF_SD_BLE_API_VERSION >= 5 // We use the "polling" dispatch model // http://infocenter.nordicsemi.com/topic/com.nordic.infocenter.sdk5.v14.2.0/group__nrf__sdh.html?cp=4_0_0_6_11_60_20#gab4d7be69304d4f5feefd1d440cc3e6c7 // This will process any pending events from the Softdevice nrf_sdh_evts_poll(); #else intern_softdevice_events_execute(); #endif core_util_critical_section_enter(); } core_util_critical_section_exit(); }
Timer::~Timer() { core_util_critical_section_enter(); if (_running) { if(_lock_deepsleep) { sleep_manager_unlock_deep_sleep(); } } _running = 0; core_util_critical_section_exit(); }
void sleep_manager_lock_deep_sleep_internal(void) { core_util_critical_section_enter(); if (deep_sleep_lock == USHRT_MAX) { core_util_critical_section_exit(); error("Deep sleep lock would overflow (> USHRT_MAX)"); } core_util_atomic_incr_u16(&deep_sleep_lock, 1); core_util_critical_section_exit(); }
void set_time(time_t t) { core_util_critical_section_enter(); if (_rtc_init != NULL) { _rtc_init(); } if (_rtc_write != NULL) { _rtc_write(t); } core_util_critical_section_exit(); }
void sleep_manager_unlock_deep_sleep_internal(void) { core_util_critical_section_enter(); if (deep_sleep_lock == 0) { core_util_critical_section_exit(); error("Deep sleep lock would underflow (< 0)"); } core_util_atomic_decr_u16(&deep_sleep_lock, 1); core_util_critical_section_exit(); }
void lp_ticker_init() { if(!rtc_reserved) { core_util_critical_section_enter(); rtc_init_real(RTC_INIT_LPTIMER); rtc_set_comp0_handler((uint32_t)lp_ticker_irq_handler); rtc_reserved = 1; core_util_critical_section_exit(); } }
void us_ticker_set_interrupt(timestamp_t timestamp) { // Set SCT3 match register 0 (critical section) core_util_critical_section_enter(); LPC_SCT3->CTRL |= (1 << 2); LPC_SCT3->MATCH0 = (uint32_t)timestamp; LPC_SCT3->CTRL &= ~(1 << 2); core_util_critical_section_exit(); // Enable interrupt on SCT3 event 0 LPC_SCT3->EVEN = (1 << 0); }
void InterruptIn::fall(Callback<void()> func) { core_util_critical_section_enter(); if (func) { _fall.attach(func); gpio_irq_set(&gpio_irq, IRQ_FALL, 1); } else { _fall.attach(NULL); gpio_irq_set(&gpio_irq, IRQ_FALL, 0); } core_util_critical_section_exit(); }
bool equeue_sema_wait(equeue_sema_t *s, int ms) { int signal = 0; Timeout timeout; if (ms > 0) { timeout.attach_us(callback(equeue_sema_timeout, s), ms*1000); } core_util_critical_section_enter(); while (!*s) { sleep(); core_util_critical_section_exit(); core_util_critical_section_enter(); } signal = *s; *s = false; core_util_critical_section_exit(); return (signal > 0); }
void InterruptIn::rise(Callback<void()> func) { core_util_critical_section_enter(); if (func) { _rise.attach(func); gpio_irq_set(&gpio_irq, IRQ_RISE, 1); } else { _rise.attach(NULL); gpio_irq_set(&gpio_irq, IRQ_RISE, 0); } core_util_critical_section_exit(); }
void UARTSerial::sigio(Callback<void()> func) { core_util_critical_section_enter(); _sigio_cb = func; if (_sigio_cb) { short current_events = poll(0x7FFF); if (current_events) { _sigio_cb(); } } core_util_critical_section_exit(); }
void Timer::start() { core_util_critical_section_enter(); if (!_running) { if(_lock_deepsleep) { sleep_manager_lock_deep_sleep(); } _start = ticker_read_us(_ticker_data); _running = 1; } core_util_critical_section_exit(); }
void Timer::stop() { core_util_critical_section_enter(); _time += slicetime(); if (_running) { if(_lock_deepsleep) { sleep_manager_unlock_deep_sleep(); } } _running = 0; core_util_critical_section_exit(); }
void Ticker::detach() { core_util_critical_section_enter(); remove(); // unlocked only if we were attached (we locked it) and this is not low power ticker if (_function && _lock_deepsleep) { sleep_manager_unlock_deep_sleep(); } _function = 0; core_util_critical_section_exit(); }