はじめに
Linux では DMA Bufferを mmap した時に、ある条件が揃うと CPU Cache が無効になり、パフォーマンスが極端に落ちる場合があります。そこで、何故そのようなことが起こるのか説明します。少し長くなるので、次のように記事を幾つかに分けて投稿します。
- はじめに
- Cache Coherence 問題
2.1 Cache Coherence 問題とは何か(この記事)
2.2 Cache Coherence 問題の解決方法 - Cache Aliasing 問題
- Linux Kernel の Cache 問題の扱い
- Linux では Cache Coherence Hardware を持っていないとDMA Buffer をmmap する際に CPU Cache が無効になる
- Raspberry Pi の例
- RISC-V CPU の注意点
- 所感
1〜3は、コンピューターアーキテクチャの基本的な事項を、簡単に説明したものです。すでにご存じの方は読み飛ばしてください。
4 はこれらの問題を Linux Kernel 内でどのように扱っているかを説明します。
5 がこれらの記事群の結論です。結論だけ知りたい方はここだけ読んでください。
この記事では「Linux で DMA Bufferを mmap した時に CPU Cacheが無効になる場合がある」原因の一つである Cache Coherence 問題とは何かを説明します。すでにご存じの方は読み飛ばしてください。
Cache Coherence 問題とは何か
Cache Coherence 問題は一言でいえば CACHE と MEMORY とのデータの一貫性(Coherence) の問題です。
なお、厳密に言えば、Cache Cohrence 問題と言えば、複数のCPU が各々持っている CACHE 間とのデータの Coherence問題も含まれます。しかし、ここでは DMA Bufferがおかれる MEMORY と CPUの CACHE との間の Coherence問題に絞って説明します。
CPUが DMA Buffer に書き込んで DEVICE が読む場合
まず、CPU が DMA Buffer にデータを書き込んで、DEVICE が DMA を使って DMA Buffer を読む場合を考えます。その場合は次の図のように処理が進みます。
Fig.1 Cache Coherence Problem 1-1
- CPU が MEMORY 上の DMA Buffer にデータの書き込みを要求します。
図の例ではaddr=0x0080 に data=0xABED の書き込みを要求しています。 - CACHE が有効な場合は、MEMORY への書き込みは保留され、まずCACHE に書き込んだアドレスとデータが記憶されます。
図の例では D-Cache に addr=0x0080 と data=0xABED が記憶されます。
この状態では、まだ MEMORY 上にはデータが書き込まれていません。
Fig.2 Cache Coherence Problem 1-2
- 次に DEVICE が DMA を使って DMA Buffer を読みに行きます。
- しかし、MEMORY には CPU が要求したデータ書き込みの結果がまだ反映されていません。したがって、DEVICE は CPU が書き込んだデータではない内容を読んでしまいます。
これが、CPUが DMA Buffer に書き込んで DEVICE が読む場合の Cache Coherence 問題です。
DEVICE が DMA Buffer に書き込んで CPU が読む場合
次に、DEVICE が DMA Buffer にデータを書き込んで CPU が読む場合を考えます。その際、次の図のように CPU の Cache になんらかのデータがすでにキャッシュされているとします。
Fig.3 Cache Coherence Problem 2-1
- CPU が DMA Buffer からのデータを読み込んでその内容が CACHE に記録されている、あるいは CPU が DMA Buffer を初期化してその内容がすでに MEMORY に反映されているとします。この図の例では addr=0x0080 の data=0x0000 が D-Cache 上にすでに記録されています。
Fig.4 Cache Coherence Problem 2-2
- DEVICE が DMA Buffer にデータを書き込みます。
この図の例では addr=0x0080 に data=0xDEAD を書き込んでいます。
Fig.5 Cache Coherence Problem 2-3
- CPU が DMA Buffer のデータを読みます。
- しかし CACHE には DMA Buffer の前の内容が残っており、その内容が CPU に渡されます。その結果、DEVICE が DMA Buffer に書いたデータが CPU には伝わりません。
これが DEVICE が DMA Buffer に書き込んで CPU が読む場合の Cache Coherence 問題です。
まとめ
この記事では、「Linux で DMA Bufferを mmap した時に CPU Cacheが無効になる場合がある」のを説明する際に、知っておいてほしい Cache Cohernce 問題とは何かについて説明しました。
次の記事 『Linux で DMA Bufferを mmap した時に CPU Cacheが無効になる場合がある (Cache Coherence 問題の解決方法)』 では、このCache Coherence 問題の解決方法を説明します。