タスク&割り込み処理兼用API
投稿:2013-03-24
割り込み処理から呼び出しできるAPIは例えば「xQueueSendToBackFromISR」といった「~FromISR」形式のものだけです。
汎用関数からAPIを呼ぶ際、呼出元が割り込み処理の場合と、タスクの場合で2種類作るのは面倒、というかちっともスマートじゃない。
どちらから呼び出しても良い汎用関数を作りました。
ユーザマニュアルのページ731に「Interrupt Program Status Register」が記載されています。ISRフィールドが0でスレッドモード中(タスク=割り込み処理でない)、1~255が割り込み処理中なので判別できるという訳です。これを使ってAPIを切り替えたコードはこんな感じ。
void ksrk_trigger(uint32_t uSignals) { // 割り込み番号を取得(0=スレッドモード=割り込みなし) uint32_t psr = 0; __asm volatile ("mrs %0, psr" : "=r" (psr)); uint32_t isr_number = psr & 0xFF; SIGNAL_TYPE st = { NULL, uSignals, ~0, NULL }; if (0 == isr_number) { portBASE_TYPE rc = xQueueSendToBack(hSignalQue, &st, portMAX_DELAY); KSRK_ASSERT(pdTRUE == rc); } else { portBASE_TYPE HigherPriorityTaskWoken = pdFALSE; portBASE_TYPE rc = xQueueSendToBackFromISR(hSignalQue, &st, &HigherPriorityTaskWoken); KSRK_ASSERT(pdPASS == rc); if (HigherPriorityTaskWoken) { //中身はvPortYieldFromISR taskYIELD(); } } }
ありません、ほっ。