3

ターミナル サービス環境で .NET 2.0 WinForms アプリを実行すると、説明のつかない予期しない結果が発生します。私が読んだすべてのことは、JIT されたアセンブリ (つまり、NGen を使用してネイティブ イメージを作成しない) により、すべてのコード スペースがプライベート ページに格納され、ワー​​キング セットのサイズ/メモリ プレッシャーが増加することを示しています。ただし、実際の結果 (Process Explorer、VMMap、および WinDbg を使用して検証) は、JIT されたアセンブリでさえ実際に共有可能なページに配置されていることを示しています (また、アプリの複数のインスタンスが実行されている場合、別の TS の下であっても実際に共有されています)。セッション/ユーザー)。

これがなぜなのか、誰か説明できますか?これは W2K8 サーバー環境で実行されているため、ASLR は、各アセンブリの特定のベース アドレスの欠如とその結果のリベースが問題を引き起こしていない理由を説明しています。それでも、これらがネイティブの PE イメージではないという事実は、これらのアセンブリのコードがプライベート ページに格納されるという結果になるはずです。

これは、メモリ負荷を軽減するために NGen を使用して調査を開始したときに発見されましたが、JIT されたアセンブリが既に共有されていたため、実際にはワーキング セットのサイズが増加していることがわかりました。

私が見つけた最新のリファレンスはここにありますが、これも実際の調査結果とは異なります。

http://blogs.msdn.com/morgan/archive/2009/03/07/developing-net-applications-for-deployment-on-terminal-services-or-citrix.aspx

編集:最初に質問を投稿して以来、Windows Server 2003 テスト ボックスでのさらなる実験でも、明らかに JIT されたアセンブリがプロセス間で共有可能であることを示していることを追加する必要があります。私が見つけることができるすべてのアドバイスがNGenが必要であることを示している理由について、私はまだ困惑していますが、現実世界のすべての証拠はそれと矛盾しています. ここの専門家が光を当てることができることを本当に望んでいます。

ありがとう!

編集:私はすべての .NET/CLR の本を払い落としましたが、これを解決するための検索クエリのアイデアが不足しています。「何が起こっているのかわからない」というひどいしつこい気持ちを解消して、私の一日を充実させてくれるのは誰!?! :)

4

1 に答える 1

4

モジュールページを直接見ていると思います。コードを JIT すると、DLL の下には表示されません。ランタイムが割り当てるメモリに表示されます。ご覧になっているモジュール ページは、ほとんどがメタデータと IL であり、共有可能なのはそのためです。

実験として、30K の静的メソッドを生成して呼び出す小さなプログラムを作成しました。私のシステムでは、このプログラムの JIT バージョンには 8.2 MB のプライベート コミット メモリがあり、NGEN バージョンには 3.8 MB あります。

ただし、モジュール ページ内であっても、NGEN はメモリの使用に役立ちます。ランタイムが NGEN イメージをロードできる場合、コードを JIT するためにモジュールのメタデータを読み取る必要はありません。私のテスト アプリケーションの JIT バージョンは、2.3MB のワーキング セットを使用しています。NGEN バージョンは 32 キロバイトを使用しています。

NGEN は起動時間にも役立ちます。ウォーム スタートアップ時間への影響は無視できる場合がありますが、コールド スタートアップ時間への影響 (ディスクからすべてのページの読み取りを節約する) は顕著になる可能性があります。

于 2009-04-18T14:46:26.233 に答える