如何从 firefox-addon / js-ctypes 调用C++类实例

How to call a C++ class instance from firefox-addon / js-ctypes?

本文关键字:调用 C++ 实例 js-ctypes firefox-addon      更新时间:2023-10-16

我有一个DLL(带有这样的c ++代码):

MyObject::MyObject(TYPEPERIPH typePeriph) {
    m_TypePeriph = typePeriph;
    //..
}
CR MyObject::GetTypePeriph( TYPEPERIPH *typePeriph ) const throw(MY_Exception) {
    *typePeriph = m_TypePeriph;
    //..
    return 0;
}

这在C++中被称为,就像这样:

MyObject MyObject((TYPEPERIPH)myTypePeriph);
MyObject.GetTypePeriph(&result);

我想用js-ctypes调用这个DLL:

Components.utils.import("resource://gre/modules/ctypes.jsm");
var dll = ctypes.open("my.dll");
var constructor = dll.declare('MyObject',
    ctypes.default_abi,
    ctypes.voidptr_t,
    ctypes.uint8_t
);
var ptr=constructor( 1 ) // ptr seems to be a pointer to an instance
// but how to call this instance ?? should I pass the ptr somewhere ?
var GetTypePeriph = dll.declare('GetTypePeriph',
    ctypes.default_abi,
    ctypes.int,
    ctypes.uint8_t.ptr
);
var result=ctypes.uint8_t(0);
GetTypePeriph(result.address());
myPerif= result.value;

第一部分工作(^^)..."PTR"似乎是一个有效的指针。但是我不知道如何使用此指针调用实例方法...

您必须定义 VTABLE,然后创建一个实例,请参见此处 - https://developer.mozilla.org/en-US/docs/Mozilla/js-ctypes/Examples/Using_COM_from_js-ctypes

上周我还用js-ctypes做了一些COM,我在Windows上使用DirectShow API - https://github.com/Noitidart/ostypes_playground/commits/audio-capture

VTBLE 方法必须井井有条!!我花了大约两个月的时间才弄清楚我什么时候第一次进入它。

以下是我做的一堆COM东西的定义:https://github.com/Noitidart/ostypes/compare/fb1b6324343d6e19c942bbc0eb46cfcfbe103f35...master

我编辑了您的代码,使其看起来更像:

Components.utils.import("resource://gre/modules/ctypes.jsm");
var dll = ctypes.open("my.dll");
var MyConstructorVtbl = ctypes.StructType('MyConstructorVtbl');
var MyConstructor = ctypes.StructType('MyConstructor', [
    { 'lpVtbl': MyConstructorVtbl.ptr }
]);
MyConstructorVtbl.define([
    {
        'GetTypePeriph': ctypes.FunctionType(ctyes.default_abi,
            ctypes.int, [           // return type
                MyConstructor.ptr,  // arg 1 HAS to be ptr to the instance EVEN though your C++ above doesnt show this. this is how it works.
                ctypes.uint8_t.ptr
            ]).ptr
    }
]);
var constructor = dll.declare('MyObject',
    ctypes.default_abi,
    MyConstructor.ptr.ptr,
    ctypes.uint8_t
);
var ptr=constructor( 1 ) // ptr seems to be a pointer to an instance
var instance = ptr.contents.lpVtbl.contents;
var result=ctypes.uint8_t(0);
instance.GetTypePeriph(ptr, result.address());
myPerif= result.value;