Open棟梁Project - マイクロソフト系技術情報 Wiki -[[戻る>メモリ・リーク]] * 目次 [#d5d0a567] #contents *概要 [#se5f4d1e] -マネージ・リソースであれば、GCで適切に解放される。~ -このため、マネージ・オブジェクトでリークするものは、~ 関数スタックに積まれるローカル変数以外に保持されたマネージ・オブジェクトである可能性が高い。~ *GC [#h73181b8] -.NETアプリを軽快にするためのガベージ・コレクション講座 - @IT~ http://www.atmarkit.co.jp/fdotnet/directxworld/directxworld06/directxworld06_01.html **アンマネージ・リソース [#da9cceb0] アンマネージ・リソースを使用するマネージコードはリソースを明示的に解放する。~ これを怠ると、マネージコード上でGCが動作していてもメモリリークが発生する。 -マネージのユーザコードでアンマネージ・リソースをGCで適切に解放するには、以下の実装を施す必要がある。 --Marshallクラスを使用してアンマネージ・メモリ確保をする場合は~ メモリの使用後に明示的な開放が必要になるので注意する。~ アンマネージ・メモリは.NETオブジェクトと異なりGC対象とならないため。 ---Marshal クラス~ http://msdn.microsoft.com/ja-jp/library/system.runtime.interopservices.marshal.aspx -メンバにアンマネージ・リソースを持つ.NETオブジェクトには、 以下のIDisposableインターフェイスと対応する実装を施す必要がある。 --IDisposable インターフェイス~ http://msdn.microsoft.com/ja-jp/library/system.idisposable.aspx >IDisposableが適切に実装されていれば、例外時はGC任せ(未DisposeのオブジェクトはFinalizeでDisposeされる)で、正常時にClose呼び出しをするだけで良い(Close内でDisposeを呼び出すのが慣例の実装のため)。例外的にCloseやファイナライザがあってもDisposeを明示的に呼び出す必要があるものもある(旧ODP.NET)が、これは、IDisposableの実装方針に反している。オブジェクトの世代によっては解放タイミングが遅れるためファイナライザの実行タイミングも遅れることになる。これが問題となるような場合は、ファイナライザ任せで処理を実装しないこと(Disposeを明示的に呼び出す)。 **LOH [#t4a37614] -CLR 徹底解剖 大きなオブジェクト ヒープの秘密~ http://msdn.microsoft.com/ja-jp/magazine/cc534993.aspx >LOHの問題によってGen2の断片化に起因するメモリリークが発生することもある(.NET3.5までの問題)。 ***その他、LOH関係の参考資料 [#tc15305e] +The Dangers of the Large Object Heap~ http://www.simple-talk.com/dotnet/.net-framework/the-dangers-of-the-large-object-heap/~ サンプル作成者のページ +Large Object Heap fragmentation causes OutOfmemoryException 報告者 Rudiger Klaehn~ http://connect.microsoft.com/VisualStudio/feedback/details/521147/large-object-heap-fragmentation-causes-outofmemoryexception~ 上記(1)のサンプル作成者が米Microsoftに bug として報告したMicrosoftのフィードバック用ページ +.NET 航海日誌: LOH (ラージオブジェクトヒープ) でフラグメンテーションが起こる !?~ http://dotnetlogbook.blogspot.jp/2009/10/loh.html~ 上記(1)を、日本語で要約したページ +torutkの日記: .NETのメモリ管理と断片化問題~ http://d.hatena.ne.jp/torutk/20100529/p1