C++ DLL插件接口
我计划做一个 C++ 插件接口 如何从dll创建一些类(dll中的构造函数)?(с++) 但有人担心,如果使用该接口通过 MinGW 或 Borland 创建 DLL,并且 DLL 加载器是用 MSVC++ 编译的,可能会出现问题。由于唯一的导出函数被声明为 extern "C" 我不明白为什么它不起作用?
想法?
I'm planning on doing a C++ plugin interface ala How to create some class from dll(constructor in dll)?(с++)
but concerns have been raised that if the interface is used to create DLLs via MinGW or Borland and the DLL loader is compiled with MSVC++, there might be problems. Since the only exported function is declared extern "C" I fail to see why it would not work ?
Ideas ?
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(2)
如果你想跨编译器(和Release / Debug)兼容并使用C++,你需要付出更多的努力。
基本上 - 您可以传递基本数据类型和指向纯虚拟类的指针。这些类不得包含任何数据成员,它们的析构函数不得是公共的,并且它们不应具有重载函数。
内存不得在一个 dll 中分配并在另一 dll 中释放。这意味着没有例外,您需要某种引用计数或返回机制。
纯虚拟类(又名“接口”)内的所有方法都必须用调用约定标记(我更喜欢 stdcall)。
动态转换也是不可能的,因此您可能需要所有接口中的某些功能来实现这一目的(例如 COM 中的 QueryInterface)。
这是可行的,因为 win32 上的大多数编译器都尝试与 COM 兼容,并以 COM 兼容的方式解决相同的问题。为了获得第一个接口,您需要一个从 dll 导出的纯 C 函数。
如果您只使用 C 函数和 C 数据类型,一切都会正常。但这样你就只能学 C 语言,没有课程和课程。遗产。
我希望这有帮助。
名称修饰不是问题:
第一:如果您使用具有 C 数据类型的 C 函数,则所有内容都已定义,没有名称修饰(例外:在带有 STDCALL 的 VS 中,您需要通过链接器将名称重新映射到“正常”C 名称指令)
第二:类内的方法不会被导出,因此不会被破坏。您可以通过指向纯虚拟类(也称为“接口”)的指针来调用方法。这使用了偏移量并且没有名称。你仍然不能使用析构函数,因为据我所知,析构函数在 vtbl 中的位置不是固定的。
如果将结构传递给函数/方法,请务必修复对齐方式。它没有跨不同编译器定义。
If you want to be compatible across compilers (and Release / Debug) and use C++, you need a little more effort.
Basically - you are allowed to pass basic datatypes, and pointer to pure virtual classes. These classes must not contain any data member, their destructor must not be public and they should not have overloaded functions.
Memory must not be allocated in one dll and released in another. This means no exceptions and you need some kind of reference counting or returning mechanism.
All methods inside pure virtual class (aka "Interface") must be marked with a call convention (I'd prefer stdcall).
Dynamic casts are not possible as well, so you might need some functionality in all your interfaces to do the trick (like QueryInterface in COM).
This works because most compiler on win32 try to be COM compatible and solve the same problems in a COM compatible way. For getting the first interface, you need a plain C function that is exported from the dll.
If you just use C functions and C data types, everything will work as well. But then you are limited to C without classes & inheritance.
I hope that helps.
Name mangling is not a problem:
1st: if you use C functions with C data types, everything is defined, there's no name mangling (exception: in VS with STDCALL, you need to remap the name to the "normal" C name via Linker directive)
2nd: Methods inside classes are not exported and thus not mangled. You call methods via pointer to pure virtual classes (aka "Interfaces"). This uses an offset and no name. You still can't use the destructor, as the position of the destructor inside the vtbl is not fixed as far as I know.
If you pass structs to functions / methods, be sure to fix the alignment. It is not defined across different compilers.
一个想法是使用标准 extern C 函数来创建 ClassFactory。对于 dll 必须公开为有效插件的固定(或更多)入口点有一些约定。
An idea could be using standard extern C function to create a ClassFactory. Have some convenction about a fixed ( or more ) entry point the dll must expose to be a valid plugin.