現在、msp430 MCU 用のアプリケーションを開発しており、奇妙な問題が発生しています。「通常の」変数の宣言後にスコープ内で配列を宣言すると、未定義のように見える動作が発生することがあることがわかりました。このような:
foo(int a, int *b);
int main(void)
{
int x = 2;
int arr[5];
foo(x, arr);
return 0;
}
foo には 2 番目の変数としてポインターが渡されますが、これはarr配列を指していないことがあります。プログラムを 1 ステップ実行してこれを確認し、メイン スコープの arr array-as-a-pointer 変数の値が foo スコープの b ポインター変数の値と同じではないことを確認します。いいえ、これは実際には再現可能ではありません。たまにこの動作を確認しただけです。
これは、foo 関数の 1 行が実行される前でも観察できます。渡されたポインター パラメーター (b) は単に arr のアドレスを指していません。
次のように、例を変更すると問題が解決するようです。
foo(int a, int *b);
int main(void)
{
int arr[5];
int x = 2;
foo(x, arr);
return 0;
}
なぜ私たちがこの行動を経験するのかについて、誰かが何か意見やヒントを持っていますか? それとも似たような経験?MSP430 プログラミング ガイドでは、コードが ANSI C89 仕様に準拠する必要があることを指定しています。それで、配列は非配列変数の前に宣言する必要があると言っているのだろうかと思っていましたか?
これに関するご意見をいただければ幸いです。
アップデート
@Adam Shiemke と tomlogic:
宣言内の値を初期化するさまざまな方法について、C89が何を指定しているのか疑問に思っています。次のようなものを書くことは許されていますか?
int bar(void)
{
int x = 2;
int y;
foo(x);
}
もしそうなら、どうですか:
int bar(int z)
{
int x = z;
int y;
foo(x);
}
それは許されますか?以下は違法なC89に違いないと思います:
int bar(void)
{
int x = baz();
int y;
foo(x);
}
前もって感謝します。
更新 2 問題が解決しました。基本的に、関数 (foo) を呼び出す前と変数の宣言後に割り込みを無効にします。簡単な例で問題を再現することができました。解決策は、無効化割り込み呼び出しの後に _NOP() ステートメントを追加することです。
誰かが興味を持っている場合は、問題を再現する完全な例と修正を投稿できますか?
これに関するすべての入力に感謝します。