2016-12-02 10 views
2

誰かが次のコードで間違っているものを見るために、最近私に尋ね、どのように私はそれを修正する必要がありますCメモリアドレス - コードに何が問題なのですか?

// Memory-mapped peripheral 
#define STATUS_REG_ADDR 0x12345678 // 32-bit status register 
#define DATA_REG_ADDR 0x1234567C // 32-bit data register 

// Status register bits 
#define BUSY_BIT_MASK 0x00000080 // Busy bit == '1' while peripheral busy 

uint32_t get_value() 
{ 
    while (((*(uint32_t*)STATUS_REG_ADDR) & BUSY_BIT_MASK) == 1) 
     ; 

    return *(uint32_t*)DATA_REG_ADDR; 
} 

は私が前に似た何かをしたことがないので、私はIDEでそれを実行しようとしたと私は見ましたreturn文はセグメンテーション違反を与えますが、私はそれを説明する方法が分からず、何かもっと間違っているかどうかわかりません。

+0

あなたはあなたがそれを実行しているどのコンピュータでもそのアドレスから読むことができますか? (アーキテクチャ固有の理由から、ハードコードされたアドレスなのでしょうか?)また、 'x&0x80'はそのビットがセットされていれば '0x80'でなく、クリアされていればゼロでしょうか? (そして決して '1'に等しい) – e0k

+0

それは私が2,3日前に持っていた挑戦のようであり、私はそれに答えることができませんでした。私は本当にそれに答える方法を知らなかった。だから、私は、たぶん、そのようなコードで一般的に何が間違っているのか、そしてなぜそれを求めているのですか? – horatiu11

+1

[mcve] – sigjuice

答えて

4

問題はループ状態のwhileです。

BUSY_BIT_MASKは0x00000080です。 0x80とANDものは、それがLSB 0とAND 0何かが常に0

ですだとしてあなたはフラグが設定されている場合、そのので

while (((*(uint32_t*)STATUS_REG_ADDR) & BUSY_BIT_MASK) == BUSY_BIT_MASK) 

としてcondtionを変更する必要が1に等しいことはありませんそれは0x80とANDされ、出力は0x80になります。 (1 AND 1 = 1)

あなたが検討しているアドレスがあなたのコンピュータで有効ではないため、SegFaultが届きました。あなたは有効なアドレスを取らなければなりません。あなたは存在しないかもしれないランダムなメモリまたはメモリアドレスにアクセスしようとしています - それがSegFaultの理由です。

+0

お返事ありがとうございました。私は今何が起こっているのか理解しています。 – horatiu11

関連する問題