【问题标题】:How do I properly manage memory when using COM objects in VB?在 VB 中使用 COM 对象时如何正确管理内存?
【发布时间】:2010-02-28 06:51:37
【问题描述】:

谁能解释一下当我们在 COM 对象和 VB 之间传递值时,内存分配/解除分配是如何发生的。

我的担忧是: 1.

IMyInterface::Method1 ([in] BSTR* pVal, [in] SAFEARRAY(BSTR)* pArray);

我们是否需要为 COM 对象中的上述参数释放分配的内存?

2.

IMyInterface::Method2 ([in, out] BSTR* pVal);

在这种情况下,VB 会为 COM 返回值释放内存吗? (COM 对象为这些返回值分配内存)

3.

IProxy_MyInterface::Event1 ([in] BSTR* pVal);

一旦事件在 VB 内部处理,VB 是否会再次处理释放参数内存的问题?

感谢您的帮助。

谢谢

【问题讨论】:

    标签: memory-management com vb6


    【解决方案1】:

    阅读官方文档 (Allocating and Releasing Memory for a BSTR):

    http://msdn.microsoft.com/en-us/library/xda6xzx7.aspx

    这里是您所有案例的描述。

    【讨论】:

      【解决方案2】:

      [in] 参数必须由调用者分配并由调用者释放,除非 API 文档另有说明。

      [in, out] 参数不太清楚,因为这是一个 BSTR*,因此您传入的 BSTR 可能会被释放并返回不同的 BSTR,因此您应该释放返回的 BSTR 而不是您的 BSTR进来了。

      [out][out, retVal],表示内存所有权的转移,函数分配内存,然后调用者负责释放内存。

      对于 C/C++ COM 中的 BSTR,您将使用 SysAllocStringSysFreeString 进行分配和释放。

      【讨论】:

      • 感谢您的澄清,如果我使用“[out]/ [out, retVal] BSTR*”,那么被调用者有责任释放内存吗?我认为是这样,因为一旦返回一个值,调用者就无法控制该函数。请解释一下。
      【解决方案3】:

      VB6有三种字符串参数声明的情况——ByVal param As StringByRef param As StringFunction() As String。 IDL 中的第一个映射到[in] BSTR param,第二个映射到[in, out] BSTR *param,第三个映射到[out, retval] BSTR *retval

      VB6 无法声明 [in] BSTR *[out] BSTR * 参数,但它仍然可以使用这些参数,即它可以调用方法(在 VC 上)具有声明为 out-only 或任何其他 IDL 支持方式的参数的类.

      还要注意BSTR 本身是一个类型定义的指针,类似于wchar_t *,所以BSTR * 实际上是wchar **。 IDL 需要一个指向 out 参数的指针,所以你不能声明 [out] int param[out] BSTR param 也很奇怪。

      一旦[in] BSTR * 混淆清晰(输出参数需要不必要的奇怪的双重间接,但不仅仅是输入),简单的规则是,一旦你在参数声明中有一个 *,那么调用者必须在如果它不是NULL,则调用方法。

      [in, out] SAFEARRAY(BSTR)* pArray 在 VB6 中映射到 ByRef pArray() As String,您不能将其更改为 ByVal,即 VB6 需要 *,因此它不能是 in-only,调用者必须解除分配安全数组。不是 in-only 安全数组。

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2011-11-03
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2014-03-16
        相关资源
        最近更新 更多