- PR -

[C#] デリゲートをGCの対象から外す方法

投稿者投稿内容
渋木宏明(ひどり)
ぬし
会議室デビュー日: 2004/01/14
投稿数: 1155
お住まい・勤務地: 東京
投稿日時: 2007-01-28 10:21
引用:

何故そんな実装になっているのか疑問なんですけど、Callback用の メソッドがまだ一度も実行されていなかったら(つまり JIT コンパイルされていなかったら)メソッドのアドレスが不定(まだスタブのアドレス)だからなんでしょうか。サンクを通すようにすれば、コンパイルされていなくてもされていても、アンマネージ側は同じアドレスで呼び出せるからとか。



だと思われます。

引用:

で、最初の問題なのですが、やはりデリゲートインスタンスが途中で破棄されているから?



ぐらいしか、アンマネージドに渡されたコールバックアドレスが無効になるケースは思い浮かばないんですよねぇ。
yayadon
常連さん
会議室デビュー日: 2003/07/23
投稿数: 41
投稿日時: 2007-01-28 14:23
引用:

Tdnr_Symさんの書き込み (2007-01-28 02:19) より:

ところで…
System.Delegateクラスの中身を見ていると
コード:

public abstract class Delegate : ICloneable, ISerializable
{
   (省略)

// Fields
internal MethodBase _methodBase;
internal IntPtr _methodPtr;
internal IntPtr _methodPtrAux;
internal object _target;
}



_methodPtr,_methodPtrAuxってどんなポインタが入っているのだろうと気になったのですが…
リフレクションで値が見れるのかなぁ?





コンパイラで作成されるデリゲート継承クラスは,

コード:


.method public hidebysig specialname rtspecialname
instance void .ctor(object 'object',
native int 'method') runtime managed
{
} // end of method Feedback::.ctor


悲しいかな runtime managed なんですよね。
その中身は,実行時に
VES (Virtual Execution System : いわゆる実行エンジン)によって作られるので
簡単には探れないんですよね。

参考として SSCLI2.0を覗いてみても,
その機能はどこはあるの?って感じですから。

ひとつめの引数の object 'object' を _target に
ふたつめの引数の native int 'method' を _methodPtr に入れているとのことですけどね。
もちろん,本の説明どおりだという話ですが。

_methodPtrAux は,名前からすると,
thunkがネイティブ側に公開しているメソッドポインタ のような気もするけど,
逆に使った時の,
ネイティブ側のメソッドを指すポインタを入れておく場所のような気がするんですけどね...

デリゲートを逆方向に使うような場合(ネイティブ側のメソッドのラップとして使用)は,
_methodPtr と _methodPtrAux は,機能的に逆になるのだろうから,
そういうときに,Invokeは,_methodPtrAux を呼び出すんじゃないかと。
SSCLI2.0にそんなようなコメントもありますし。

SSCLI2.0どおりなら void* GetMethodPtrAux() 等で取り出せるようですが。

[ メッセージ編集済み 編集者: 稍丼 編集日時 2007-01-28 15:04 ]

スキルアップ/キャリアアップ(JOB@IT)