比較的複雑な通信インターフェイスを利用する ARM Cortex-M3 用のブートローダーを作成しています。これは、実際のアプリケーションが使用するものと同じです。アプリケーションはカーネルとして Keil の RTX を使用し、通信スタックはそれに依存しています。もちろん、GCCを使用しています。
ブートローダーは、次の基本的な手順を実行します。
- 起動時に、有効なアプリ イメージをチェックします。利用できない場合は、アップグレード モードに入ります。
- アップグレード モードに入る要求としてボタンが押されたかどうかをチェックします。それが見つかった場合は、アップグレード モードに入ります。
- 有効なイメージが見つかり、アップグレードの要求がない場合、アプリを「起動」します。
これはかなり単純化されていますが、このシナリオは目的に沿って適切に説明されています。
驚くほど困難であることが判明した最後の問題は、アプリの起動です。アイデアは、割り込みを無効にし、ベクター テーブル、スタック ポインターを設定し、新しいベクター テーブルでアプリのリセット ベクターにジャンプすることです。これはすべてピーキーに機能しますが、その後すぐにハードフォールトが発生します。
実験を通じて、単純なブートローダー (RTX や、もちろん通信スタックを使用しない) でこれを行うと、アプリの起動は正常に機能します。つまり、RTX が問題のようです。
実際のブートローダーは、アップグレード モードに入るまで RTX を必要としません。したがって、明らかなアプローチは、RTX が必要であると判断するまで RTX を開始しないことです。ただし、起動コードにハッキングされているようで、ブートローダー コードに入るまでには手遅れです。実際、ブートローダーの main() 関数はすでにスレッドです!
最善の方法は、必要になるまで RTX を開始しないことです (FreeRTOS を使用していなかったのが残念です!)。ただし、これにはハッキングが必要なようです。別のアプローチは、何らかの理由ですべての割り込みと例外を無効にすることですが、何らかの理由で、私も成功していません。誰かがどちらかのアプローチの例を持っていますか?