質問: preempt_count(); fn(data); if (preempt_count != preempt_count()) { printk(KERN_WARNING "huh, entered %p " "with preempt_count %08x, exited" " with %08x?\n", fn, preempt_count, preempt_count()); BUG(); } ``` この状態が起こるには、何が起こったのでしょうか(明らかにpreempt_countが変更されましたが、それは何が原因でしょうか?) クラッシュの他の症状は、ワークキューからi2cを実行している間に `atomic` のスケジューリングを見ていることです。これは何が原因でしょうか? 私はこのポストはロングショットだと思っていますが、私は実際にこの時点で何かトラブルシューティングを探しています。
回答: 私の頭の上からちょうど答えてください: "preempt_count"は32ビットフィールドで、さまざまな目的のためにサブビットフィールドに分割されています。サブビットフィールドは、O'Reillyの「Linuxカーネルについて」を参照してください。再び、私の頭の上から、私は "c0340000"が何を表すのか分からない。しかし、あなたが "0000010d"で始まって "0000010d"で終わったはずなので、あなたのタイマーコードが何をしていたとしてもかなり混乱しています。 1つの一般的な原因は、あなたのタイマーコードがspin_lock_bh()のようなことをしたが、spin_unlock_bh()を忘れた場合です。しかし、それは通常、preempt_countの開始と終了の値のちょうど1ビットの差になります。しかし、あなたの場合、開始値と終了値は大きな変化を示します。 マイケル