4

ポインターのみを提供するときにfree()使用される補助情報を格納するメタデータがあることは知っています。realloc()

私はヒープについてほとんど疑問を持っていません。

  • スタックはプロセスごとに割り当てられます。それには疑いの余地はありませんが、ヒープについてはわかりません。ヒープ情報がプロセスごとにグローバルに維持されるかどうかにかかわらず、その特定のプロセスに割り当てられたメモリに関する情報を保持するメカニズムがあります。

  • ヒープ情報はどのように維持されますか? ハッシュメカニズムだと思います。私もグーグルで試してみました。彼らのほとんどは、実装固有のものとして説明しました..そのように。
4

3 に答える 3

5

ヒープは、スタックと同様に、プロセスごとであり、(ほぼ)純粋にユーザースペースのものです。

ヒープマネージャは、sbrksyscallを使用して、必要なメモリ量を増やす予定であることをオペレーティングシステムに通知します。これは、ページの範囲を「不明」から「存在する、ゼロ、アクセスされない」に変更することとほとんど変わりません(これは、実際にはまだ存在しないことを意味しますが、OSは存在するふりをします)。ページが最初にアクセスされると、障害が発生し、OSはゼロプールからゼロページをプルします。
(大量のメモリが上から解放された場合、ヒープマネージャもデータセグメントを縮小する可能性があるため、少し複雑になる可能性がありますが、基本的にはそれと同じくらい簡単です)。

OSがヒープについて知っているのはこれだけです。ブロックの分割、解放されたブロックのリストまたは同様の構造への配置、ブロックの再利用など、その他すべては、プログラムの直接的または間接的(たとえば、glibcの一部として)部分であるヒープマネージャー内で行われます。

ヒープマネージャーが実行しているのは実装に依存することです。さまざまな方法で機能する、よく知られているさまざまなmalloc実装が少なくとも半ダース存在します。たとえば、これまたはこれまたはこれを参照してください。

スタックは同じまたは同様の方法で機能します。特定のメモリ範囲は、実際には何も予約せずに(つまり、ページを作成せずに)最初に「予約」されます。いくつかのページがコミットされ(つまり、作成され)、最後のページは書き込み保護されているか存在しないかのいずれかであり、これは特別な方法で記憶されます。スタックが大きくなり、この最後のページに触れると、障害が発生します。次に、スタックがまだ許容サイズ内にある場合、新しいページがゼロプールからプルされます。

プロセスが終了すると、それらのページへのすべての参照が削除され、(参照を保持している別のプロセスと共有されていない場合)優先度の低いバックグラウンドタスクに渡され、ゼロにされて「ゼロプール」に追加されます。

于 2012-07-16T10:09:14.507 に答える
2

はい、ヒープもプロセスごとです。

ロック競合を減らすためにスレッドごとのヒープを使用するヒープ実装がありますが、それは (ユーザー空間) ヒープ マネージャーの実装の詳細です。

于 2012-07-16T09:29:37.677 に答える