V8 向け ActiveXObject、なんとか動いた
というわけで、先日からごそごそとやっている V8 用 COM/OLE 対応コードですが、なんか別の URL を使ってみたら動きました。悲しすぎる。
要するにどういうものかというと、OLE オートメーションに対応しているオブジェクトを Javascript コードからオブジェクトとして触ることができます。逆に、Javascript オブジェクト(と関数)を dispatch interface として COM 側からアクセスすることができるようになります。
まだ JS オブジェクトの export の動作検証や ITypeInfo 関係のコードなどは書いていないのですが、相手が動的言語のオブジェクトなのである程度手抜きしてもいい…のかなあ。
とりあえずサンプルですが、こんな感じで使えます。なんとなく IE の Javascript みたいな感じでしょ?
V8 shell 0.4.9.3 + COM support > var o = new ActiveXObject('Msxml2.XMLHTTP') ActiveXObject(021E3A68) construct @ 003EACD0 > o.onreadystatechange = function() { print('readyState=' + o.readyState); } function () { print('readyState=' + o.readyState); } > o.open('GET', 'http://d.hatena.ne.jp/tossy-2/', false) ActiveXFunction(021E3A68, 1) construct @ 003E6AF8 readyState=1 > o.send() ActiveXFunction(021E3A68, 5) construct @ 003E6A68 readyState=1 readyState=2 readyState=3 readyState=4 > var t = o.responseText > t.length 30493
で、以前書いたとおり、Javascript インスタンスの GC にあわせて C++ オブジェクトがデストラクトされるようにしかけをしているのですが、まだ若干微妙。どこかで参照が残っているのかもしれない。
Javascript のメソッド呼び出しは (1) メンバを lookup → (2) 関数が返ってくる → (3) 呼び出し、という流れになるので、IDispatch のメンバ呼び出しをラップするには関数 closure 的なオブジェクトが必要になります。ActiveXFunction というオブジェクトがその役目を果たしているのですが、こいつがまったく GC で回収される気配がないので困っています。
> o = undefined > gc() ActiveXObject@003EACD0 destruct >