加载dll时JNA调用CoInitialize

时间:2014-11-11 18:43:45

标签: java delphi dll jna

我有一个用Pascal写的dll。我已经确定我需要在Java代码中运行CoInitialize,但我无法弄清楚如何。

我找到了另一个应该在这里提供帮助的Stack Overflow线程:https://stackoverflow.com/questions/15763993但我无法理解它是如何工作的。

我现在的代码是:

public interface CSQLLib extends StdCallLibrary {

    CSQLLib INSTANCE = (CSQLLib) Native.loadLibrary("DatabaseLibrary", CSQLLib.class);

    public HRESULT CoInitialize(Pointer p);

    public HRESULT CoUninitialize();

    public String doSQLQuery(String input);
    public void DllMessage();
}

1 个答案:

答案 0 :(得分:1)

使用 JNA 从 Java 代码调用 CoInitializeEx 的示例:

import com.sun.jna.platform.win32.Ole32;

public class Example {
  public static void main(String[] args) {
    Ole32.INSTANCE.CoInitializeEx(null,Ole32.COINIT_APARTMENTTHREADED);
  }
}

请注意,JNA docsWindows SDK docs 都推荐使用 CoInitializeEx 而不是 CoInitializeCoInitialize(null) 等价于 CoInitializeEx(null,Ole32.COINIT_APARTMENTTHREADED),但 JNA 文档建议在 Java 应用程序中使用 COINIT_MULTITHREADED(实际上,他们称其为“唯一明智的选择”)——然而,不管他们怎么说,某些 COM 接口只能与 COINIT_APARTMENTTHREADED 一起正常工作,因此它实际上取决于您使用的 COM 对象。无论您选择哪种方式,CoInitializeEx 都更好,因为它可以清楚地(而不是隐含地)您使用的是哪种 COM 线程模式。

请注意您在评论中提到的解决方案,从用 Delphi 编写的 DLL 中调用 CoInitialize 不是一个好习惯。 COM 应该在应用程序中而不是在 DLL 中初始化。如果您曾尝试在某个其他应用程序中重用您的 DLL(该应用程序已经在调用 CoInitialize/CoInitializeEx),您对它的调用很可能会因 S_FALSE 或 {{1} 而失败} 因为应用程序已经初始化了它。