2

ここに示すアイドルフックを作成しました

void vApplicationIdleHook( void )
{
    asm("nop");
    P1OUT &= ~0x01;//go to sleep lights off!
    LPM3;// LPM Mode -  remove to make debug a little easier...
    asm("nop");
}

これにより、LEDがオフになり、何もすることがないときにMSP430がスリープ状態になります。いくつかのタスク中にLEDをオンにします。

また、MCUをウェイクアップする可能性のある割り込みの終了時にSRのスリープモードビットを変更するようにしました(portext.s43のスケジューラティックisrを除く。iarのマクロは

__bic_SR_register_on_exit(LPM3_bits);   // Exit Interrupt as active CPU

ただし、MCUをスリープ状態にすると、不規則な動作が発生するようです。LEDは常にオンのままですが、スコープを設定すると、割り込みの1つ(UART)を介してmcuをウェイクアップし、その後再びオンになるたびに、数命令サイクルの間オフになります。LPM3の指示をコメントアウトすると、計画どおりに進みます。LEDはほとんどの時間オフのままで、タスクが実行されているときにのみオンになります。

MSP4f305438を使用しています

何か案は?

4

1 に答える 1

3

おそらく問題は、__bic_SR_register_on_exit(LPM3_bits) の呼び出しです。このマクロは、スタックされた SRの LPM ビットを変更するため、スタック上の保存された SR の場所を認識している必要があります。__bic_SR_register_on_exit() は、__interrupt ディレクティブを使用するときにコンパイラによって生成される標準の割り込みスタック フレーム用に設計されていると思います。ただし、RTOS は完全なコンテキストを格納する必要があるため、FreeRTOS のようなプリエンプティブ RTOS は通常、コンパイラによって生成されるスタック フレームよりも大きい独自のスタック フレームを使用します。この場合、ISR から呼び出された __bic_SR_register_on_exit() は、スタック上で SR を見つけられない可能性があります。さらに悪いことに、スタックに保存されている他のレジスタ値が破損する可能性があります。

プリエンプティブ カーネルの場合、ISR から __bic_SR_register_on_exit() を呼び出しません。その結果、アイドル コールバックは 1 回だけ呼び出され、二度と呼び出されません。これは、RTOS がアイドル タスクに戻るコンテキスト スイッチを実行するたびに、LPM ビットがオンになった状態で SR が復元されるためです。これにより、スリープモードが発生しますが(これが必要です)、LEDは切り替えられません。

Miro Samek state-machine.com

于 2010-03-16T13:22:02.387 に答える