5

誰かがC#の任意のタイプのオブジェクトでそれが可能である理由を詳細に説明できますか?lock

lockのために、どのように使うのか理解しています。私はそれがMonitor.Enter/にどのように拡張するかを知っていますExit。実装の詳細と設計上の考慮事項の説明を探しています。

まず第一に:内部で何が起こっているのですか?例:オブジェクトインスタンスに(RTTI / vtableの場合のように)それを機能させる余分なビットがありますか?または、オブジェクト参照をキーとするある種のルックアップテーブルですか?(もしそうなら、これはGCとどのように相互作用しますか?)または何か他のもの?ロックデータが何であれ、保持するために特定のタイプのインスタンスを作成する必要がないのはなぜですか?

(ちなみに、ネイティブコードでは何をしEnterてマップしますか?)Exit

そして、第二に、なぜ.NETはロックを解除するための特定のタイプを持たないように設計されているのですか?(とにかく目的のために作成するのが一般的であり、new object()「古いオブジェクト」をロックするほとんどの場合は問題があります。)この設計の選択は、実装の詳細によって強制されましたか?それとも意図的でしたか?そして、意図的にすれば、それは良い選択でしたか?(この2番目の部分には推測が必要な場合があることを理解しています。)

4

1 に答える 1

4

lockすべての非structタイプで可能です。ヒープ上の各参照タイプのレイアウトには、ロックを管理するために使用される特別なフィールド (同期ブロック) があります。レイアウトについては、 CLR がランタイム オブジェクトを作成する方法 で詳しく説明されています。記事の抜粋は次のとおりです。

OBJECTREF は、オブジェクト インスタンスの先頭ではなく、DWORD オフセット (4 バイト) を指しています。DWORD はオブジェクト ヘッダーと呼ばれ、SyncTableEntry テーブルへのインデックス (1 から始まる syncblk 番号) を保持します。

ヒープ上のオブジェクト レイアウト:

sync block index 
pointer to type
fields...

憶測の部分: 元のガイダンスは都合の良いものは何でもロックすることだったと思いますが、メソッドをデッドロックする外部コードを取得しやすいため、比較的すぐに特別な「ロック用のプライベート オブジェクト」を持つように変更されました。フレームワークには、公開されているオブジェクトをロックすることを余儀なくされたクラスさえあったと思います...

于 2012-11-26T01:01:29.463 に答える