C言語の基礎
#define GPIO_BASE 0x40020000u
volatile uint32_t *const odr =
(volatile uint32_t *)(GPIO_BASE + 0x14);
*odr |= 1u << 5;マイコンの出力レジスタを、上のように宣言して使っている。この宣言についての説明として、正しいものはどれか。
- A*odr の値は書き換えられず、odr のほうは割り込みで変わることがあるので、使うたびに読み直される
- Bvolatile を付けたので、*odr |= 1u << 5 の読み出し・変更・書き込みが、途中で割り込まれない一続きの操作になる
- Codr が指す番地は変えられず、odr を通した読み書きは省略されずに、書いた回数だけ実際に行われる
答えと解説を見る
正解:C. odr が指す番地は変えられず、odr を通した読み書きは省略されずに、書いた回数だけ実際に行われる
const が * の右にあるので、odr というポインタ自体が変えられず、常に同じレジスタの番地を指すことを表します。指す先の uint32_t には volatile が付いているので、コンパイラは *odr の読み書きを省いたりまとめたりせず、書いた回数だけ実際にアクセスします。ただし volatile は操作を不可分にはしないので、*odr |= … の読み出しと書き込みの間に割り込みが入ることはあります。割り込みハンドラと同じレジスタを操作する場合は、その間だけ割り込みを禁止するか、ビットのセット専用のレジスタを使います。
- A. const と volatile の対象を逆に読んだ説明です。const はポインタ自体に、volatile は指す先に付いています。
- B. volatile はアクセスを省かせないだけで、読み出しから書き込みまでを不可分にはしません。
- C. 正しい。ポインタ自体は const、指す先のレジスタは volatile です。