Мне нужно импортировать NPAPI DLL в приложение на C++ для моего проекта. Я следую превосходному учебнику: http://colonelpanic.net/2009/03/building-a-firefox-plugin-part-one/Импортировать NPAPI DLL в приложение C++
Однако у меня есть некоторые проблемы с доступом к методам DLL. (Примечание: в браузере DLL полностью функциональна). После вызова основных функций: NP_GetEntryPoints и NP_Initialize и извлечения ScriptableNPObject, вызов методов возвращает значение без ошибки. Имена свойств или методов одинаковы, используемые в JavaScript в браузере (функциональный регистр).
Для информации в этом примере были заменены имена свойств и методов и тип mime.
У кого-нибудь есть идея вызывать методы dll, моделируя то, что делает браузер?
Вот часть основной программы:
if (hDLL == 0)
{
std::cout << "DLL failed to load!" << std::endl;
}
else
{
std::cout << "DLL loaded!" << std::endl;
//WRAP NP_GETENTRYPOINTS FUNCTION:
_GetEntryPointsFunc = (GetEntryPointsFunc)GetProcAddress(hDLL, "NP_GetEntryPoints");
if (_GetEntryPointsFunc)
{
std::cout << "Get NP_GetEntryPoints Function!" << std::endl;
status = _GetEntryPointsFunc(pFuncs);
}
//WRAP NP_INITIALIZE FUNCTION:
_InitializeFunc = (InitializeFunc)GetProcAddress(hDLL, "NP_Initialize");
if (_InitializeFunc)
{
std::cout << "Get NP_Initialize Function!" << std::endl;
status = _InitializeFunc(&sBrowserFuncs);
}
int32_t mode = NP_EMBED;
int32_t argc = 7;
static const char mimetype[] = "application/x-mime_type_of_my_plugin";
char * argn[] = {"param1", "param2", "param3", "param4", "param5", "param6", "param7"};
char * argv[] = { "value1", "value2", "value3", "value4", "value5", "value6", "value7" };
NPObject np_object;
uint16_t size;
char* descritpionString;
char* nameString;
instance = &(plugin_instance.mNPP);
status = pFuncs->newp((char*)mimetype, instance, (uint16_t)mode, argc, argn, argv, &saved);
status = pFuncs->version; //OK
status = pFuncs->getvalue(instance,NPPVpluginDescriptionString,&descritpionString); //OK
status = pFuncs->getvalue(instance,NPPVpluginNameString,&nameString); //OK
status = pFuncs->getvalue(instance,NPPVpluginScriptableNPObject,&np_object); //ISSUE STARTS HERE
std::cin.get();
}
Вот моя функция create_object вызывается после получения поддерживающих сценариев NPObject с ПолучитьЗначением функции:
NPObject* _createobject(NPP npp, NPClass* aClass)
{
if (!npp) {
return nullptr;
}
if (!aClass) {
return nullptr;
}
NPObject *npobj;
if (aClass->allocate) {
npobj = aClass->allocate(npp, aClass);
} else {
npobj = (NPObject *)malloc(sizeof(NPObject));
}
if (npobj) {
npobj->_class = aClass;
npobj->referenceCount = 1;
//TEST:
NPError status;
NPString url;
NPVariant result;
NPVariant variant;
NPIdentifier property = "existing_property";
NPIdentifier *arrayId;
uint32_t count = 2;
const char *str = "https://test_url.com";
url.UTF8Characters = str;//;
url.UTF8Length = 20;
variant.type = NPVariantType_String;
variant.value.stringValue = url;
NPVariant args[] = { variant };
status = 1; //GENERIC ERROR VALUE
status = npobj->_class->structVersion; //OK
status = npobj->_class->hasMethod(npobj,L"existing_set_function"); //STATUS OK
status = npobj->_class->enumerate(npobj, &arrayId, &count); //Privileged instruction ERROR
status = npobj->_class->hasProperty(npobj, property); //STATUS OK
status = npobj->_class->getProperty(npobj, property, &result); //STATUS OK BUT NO RESULT
status = npobj->_class->invoke(npobj,L"existing_set_function",args,1,&result); //STATUS OK
status = npobj->_class->invoke(npobj,L"existing_get_function",args,0,&result); //STATUS OK BUT NO RESULT
status = npobj->_class->invokeDefault(npobj,args,0,&result); //STATUS OK BUT NO RESULT
//END TEST
}
return npobj;
}
Наконец, здесь методы plugin_instance для объявления ndata и pdata:
nsNPAPIPluginInstance::nsNPAPIPluginInstance()
{
mNPP.pdata = NULL;
mNPP.ndata = this;
}
nsNPAPIPluginInstance::~nsNPAPIPluginInstance()
{
}
Заранее благодарен.
I hadn 't протестировал NP_CLASS_STRUCT_VERSION_ENUM, и эффективно функция перечисления недоступна, спасибо. Я изменил использование NPIdentifiers и протестировал программу на простом тестовом плагине. Он отлично работает: простой плагин вызывает NPN_utf8fromidentifier и метод вызывается. Но он не работает с плагином для импорта. Я также протестировал NPObject после возврата NPN_CreateObject(), но никакого эффекта: методы не вызывают и никакой вызов не выполняется для любых функций API. Возможно ли, что плагин использует некоторые ресурсы браузера вне функций API? – JeH
Что вы имеете в виду, «методы не вызывают», возвращает ли она ошибку? Вы тестировали свое использование NPIdentifier с помощью своего тестового плагина, делая что-то вроде 'if (nameArg == NPN_GetStringIdentifier (" methodName ") ...' Всегда возможно, что плагин делает странные вещи или глючит, но это может быть гораздо проще. –
Я имею в виду, что «метод не вызывает», что функция invoke возвращает false.Да, я тестировал использование NPIdentifier в тестовом плагине, и он отлично работает. Я объявляю свой NPidentifier следующим образом: NPIdentifier method = "method_name"; Контрольный плагин вызывает, как ожидалось, функцию NPN_utf8fromidentifier для преобразования, но другой плагин ничего не делает. Да, я уверен, что это более простая проблема. – JeH