CPU<---Cache<---Memory<---Device
DeviceからMemoryにDMAでデータを転送して、そのデータをCPUで読む場合、以下のどちらの操作が必要か。
1. DeviceからMemoryへの転送前に、cacheのinvalidate(cacheの内容を捨てる)をする。
3. DeviceからMemoryへの転送後に、cacheのinvalidateをする。
答えは、
「1が正しく、3だと正しくデータが読めない事がある」
3.だとダメな理由は以下の通り。
--------
例として、DMA転送先のアドレスを0xa0000000とする。
3.は、以下のように細分化できる。
3-1 0xa0000000の内容(古い内容)が、既にcache上にある。
3-2 DeviceからMemoryの0xa0000000へDMA転送を開始する。
3-3 DMAの完了を待つ。
3-4 0xa0000000の古い内容がcacheにあるので、それをinvalidateする。
3-5 0xa0000000の新しい内容をMemoryから読む。
問題は、3-3の間に0xa0000000の古い内容がcacheから追い出されてしまい、新しい0xa0000000の内容を古い内容で上書きしてしまう可能性がある事。
3-3の間に、他のスレッドが頻繁にメモリアクセスを行うなどすると、0xa0000000の古い内容がcacheから追い出されやすい。
google-code-prettify
2008-11-22
2008-11-20
[クイズ]DMAをする時に、いつcacheを操作するか
CPU<---Cache<---Memory<---Device
DeviceからMemoryにDMAで転送して、そのデータをCPUで読む場合、以下のいずれかのcacheの操作を行う必要がある。
1. DeviceからMemoryへの転送前に、cacheのinvalidate(cacheの内容を捨てる)をする。
2. DeviceからMemoryへの転送前に、cacheのflush(cacheの内容をMemoryへ書き出す)する。
3. DeviceからMemoryへの転送後に、cacheのinvalidateをする。
2.はflushの分遅くなるが、実質1.と変わり無い。これらの32つのうちどれかを行えば、正しくDMA転送ができる。
…のだと、ずっと思っていた。
今日まで。
ところが、上記のうち1つは正しくない事に、この歳になって今さらながら気付いた。
■クイズ
上記の3つ1と3のうち、正しくデータを読めないのはどれか。
また、正しくデータを読めない理由は何か。
■訂正
2.もダメでしたね。1.と3.の2択に変更しました。
DeviceからMemoryにDMAで転送して、そのデータをCPUで読む場合、以下のいずれかのcacheの操作を行う必要がある。
1. DeviceからMemoryへの転送前に、cacheのinvalidate(cacheの内容を捨てる)をする。
3. DeviceからMemoryへの転送後に、cacheのinvalidateをする。
…のだと、ずっと思っていた。
今日まで。
ところが、上記のうち1つは正しくない事に、この歳になって今さらながら気付いた。
■クイズ
上記の
また、正しくデータを読めない理由は何か。
■訂正
2.もダメでしたね。1.と3.の2択に変更しました。
2008-11-18
subversionのpost-commitフックで、pipeがつまるのを修正
以前作った、commit時にメールを送るpost-commitだが、変更ファイル数が多い時に、pipeがつまって止まってしまう事がわかったので、修正した。
以前のバージョン:
これだと、
・nkf側が、JISに変換した結果をwriteしようとする
・post-commit側もwrite中
の時に、デッドロックする。
selectを使うという手もあったが、もっと単純に、テンポラリファイルを作って対処する事にした。
以前のバージョン:
(nkfr, nkfw) = popen2.popen('nkf -j')
nkfw.write(log2)
nkfw.close()
jislog = nkfr.read()
nkfr.close()これだと、
・nkf側が、JISに変換した結果をwriteしようとする
・post-commit側もwrite中
の時に、デッドロックする。
selectを使うという手もあったが、もっと単純に、テンポラリファイルを作って対処する事にした。
(fd, tname) = tempfile.mkstemp()
os.write(fd, log2)
os.close(fd)
(nkfr, nkfw) = popen.popen2('nkf -j %s' % (tname,))
nkfw.close()
jislog = nkfr.read()
nkfr.close()
os.unlink(tname)
2008-11-17
Enigmailで使っていたPGPのprivate keyを、他のPCに移行する
$ c:\Program Files\GNU\GnuPG\gpg.exe --export-secret-keys > mykey.asc
あとはこのファイルをEnigmailでimportしてやれば良い。
登録:
投稿 (Atom)