Linuxカーネルのメモリ制限


12

困惑している問題があります。sgを使用してカスタマイズされたCDBを実行するライブラリがあります。sgのメモリ割り当てに日常的に問題があるシステムがいくつかあります。通常、sgドライバーには約4mbのハード制限がありますが、これらの少数のシステムでは〜2.3mbのリクエストでそれが見られます。つまり、CDBは2.3MBの転送を割り当てる準備をしています。ここに問題はないはずです:2.3 <4.0。

今、マシンのプロファイル。64ビットCPUですが、CentOS 6.0 32ビットを実行します(ビルドもしなかったし、この決定とは関係ありません)。このCentOSディストリビューションのカーネルバージョンは2.6.32です。16GBのRAMがあります。

システムでのメモリ使用量は次のようになります(ただし、このエラーは自動テスト中に発生するため、このerrnoがsgから返されるときの状態を反映しているかどうかはまだ確認していません)。

top - 00:54:46 up 5 days, 22:05,  1 user,  load average: 0.00, 0.01, 0.21
Tasks: 297 total,   1 running, 296 sleeping,   0 stopped,   0 zombie
Cpu(s):  0.0%us,  0.0%sy,  0.0%ni,100.0%id,  0.0%wa,  0.0%hi,  0.0%si,  0.0%st
Mem:  15888480k total,  9460408k used,  6428072k free,   258280k buffers
Swap:  4194296k total,        0k used,  4194296k free,  8497424k cached

私が見つかりました。この記事からのLinuxジャーナルカーネルのメモリ割り当てについてです。この記事は日付が付けられていますが、2.6に関係しているようです(筆者に関する筆者のコメント)。この記事では、カーネルは約1GBのメモリに制限されていると述べています(ただし、その1GBが物理、仮想、または合計の場合、テキストからは完全には明らかではありません)。これが2.6.32の正確なステートメントかどうか疑問に思っています。最終的には、これらのシステムがこの制限に達しているのではないかと思っています。

これは実際には私の問題に対する答えではありませんが、2.6.32の主張の真実性について疑問に思っています。それでは、カーネルの実際のメモリ制限は何ですか?これは、トラブルシューティングの考慮事項である必要があります。他の提案は大歓迎です。これを困惑させているのは、これらのシステムが、同じ問題を示さない他の多くのシステムと同一であることです。

回答:


21

32ビットシステムでのLinuxカーネルメモリの1 GiB制限は、32ビットアドレス指定の結果であり、かなり厳しい制限です。変更することは不可能ではありませんが、非常に正当な理由でそこにあります。変更すると結果が生じます。

Linuxが作成されていた1990年代初頭のウェイバックマシンを見てみましょう。当時、Linuxを2 MiBのRAMで実行できるのか、それとも本当に4 MiB全体必要なのかという議論がありました。もちろん、16台のMiBモンスターサーバーを備えたハイエンドスヌーブはすべて私たちを冷笑していました。

その面白い小さなビネットは何と関係がありますか?その世界では、単純な32ビットのアドレス指定から得られる4 GiBのアドレス空間をどのように分割するかを簡単に決定できます。いくつかのOSは、単に「カーネルフラグ」などのアドレスの最上位ビットを処理し、それを半分に分割する:アドレス0〜2 31 -1トップビットは、クリアされ、ユーザ空間のコードのためにあったとアドレス2 31 2を介して32 - 1は最上位ビットが設定されており、カーネル用でした。アドレスを見て、次のように伝えることができます:0x80000000以上、それはカーネル空間です。それ以外の場合はユーザー空間です。

PCメモリサイズが4 GiBのメモリ制限に向かって膨れ上がったため、この単純な2/2分割が問題になり始めました。ユーザー空間とカーネル空間はどちらも大量のRAMに対して良い主張がありましたが、コンピューターを使用する目的は一般にカーネルを実行するのではなく、ユーザープログラムを実行することであるため、OSはユーザー/カーネルの分割で遊び始めました。3/1スプリットは一般的な妥協案です。

物理対仮想についての質問については、実際には問題ではありません。技術的に言えば、これは仮想メモリの制限ですが、それはLinuxがVMベースのOSだからです。32 GiBの物理RAMをインストールしても何も変更されず、swapon32 GiBスワップパーティションにも役立ちません。何をしても、32ビットLinuxカーネルは4 GiBを超えるアドレスを同時に処理することはできません。

(はい、PAEについて知っています。64ビットOSがついに引き継いでいるので、その厄介なハッキングを忘れることができることを望みます。とにかくこの場合に役立つとは思いません。)

要するに、1 GiBのカーネルVM制限に達した場合、2/2の分割でカーネルを再構築できますが、それはユーザースペースプログラムに直接影響を与えます。

64ビットは本当に正しい答えです。


1
ありがとう。この記事はすばらしいです。Windowsで一般的に使用される2/2分割に遭遇しました。そのとき、Linuxは3/1スプリットを使用していることを知りました。記事を読んだときに、点をつなげたと思うと思いました。だから...これは私がこれを覚えておく必要があるように聞こえます。これらのシステムがテストの性質を考慮して限界に達しつつあると考えるのは、おそらくそれほど遠くないでしょう。大きな問題は、なぜ他のシステムもこれを経験していないのかということです。再度、感謝します。
アンドリューファランガ14年

1
@AndrewFalanga:実際、現代のWindowsはファジー3/1スプリットも使用しています。
ウォーレンヤング14年

1
私たちの中には、SSCから継承した3つの異なるマシンのメモリを組み合わせて、12 MBのサーバーを取得することができました。だから、ずっと私たちは望んでいた何でもできるメモリ...
dmckee ---元司会者の子猫

3
「はい、x86セグメントメモリモデルについて知ってます。32ビットOSがついに引き継いでいるので、その厄介なハックを忘れることができることを願っています。」
CVn 14年

32ビットと64ビットの間の倍増は16ビットと32倍の2倍あります。これは、このようなハッキングを延期するために必要な時間を2倍にします。しかし、他のすべては平等ではありません。ムーアの法則の廃止に伴い。32ビットのx86コンピューティングから20年が経ちました。64ビットから何世紀もかかる可能性があります。今日のDRAM帯域幅での2バイトのRAMのシングルパス読み取りには、約30 かかります。64ビットの制限に近づくために、帯域幅の増加はどこから来るのでしょうか?
ウォーレンヤング14年

2

ウォーレンヤングの優れた答えに少し付け加えたいと思います。なぜなら、実際には彼が書いているよりも悪いからです。

1GBのカーネルアドレス空間は、さらに2つの部分に分かれています。128MB vmallocはで、896MBはlowmemです。それが実際に何を意味するか気にしないでください。メモリを割り当てるとき、カーネルコードは、これらのどれを使用するかを選択する必要があります。空きスペースがあるプールからメモリを取得することはできません。

を選択するとvmalloc、128MBに制限されます。1GBはそれほど悪くないようです...

を選択するとlowmem、896MBに制限されます。1GBからそれほど遠くはありませんが、この場合、すべての割り当ては次の2のべき乗に切り上げられます。したがって、2.3MBの割り当ては実際に4MBを消費します。また、を使用する場合、1回の呼び出しで4MB以上を割り当てることはできませんlowmem

64ビットは本当に正しい答えです。


あなたの答えに関連した質問があります。lowmemという名前のこのメモリ空間に対して、kmallocやkzmallocなどの呼び出しからのメモリはどこから来たのでしょうか?
アンドリューファランガ

@AndrewFalanga、はい、これらの関数はlowmemを使用します。
ウゴレン
弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.