MIDL 数组

数组声明符在 IDL 文件的接口正文中显示为以下项之一:

  • 常规声明的一部分
  • 结构或联合声明符的成员
  • 远程过程调用的参数

数组每个维度的边界在一对单独的方括号内表示。 计算结果为 n 的表达式表示下限为零,上限为 n - 1。 如果方括号为空或包含单个星号 (*) ,则下限为零,上限在运行时确定。

数组还可以包含用省略号分隔的两个值,这些值表示数组的下限和上限,如 [lower...upper]. Microsoft RPC 要求下限为零。 MIDL 编译器无法识别指定非零下限的构造。

数组可以与字段属性相关联 ,size_ismax_islength_isfirst_islast_is ,以指定数组的大小或包含有效数据的数组部分。 这些字段属性标识指定数组维度或索引的参数、结构字段或常量。

数组必须按以下方式与字段属性指定的标识符相关联:当数组是参数时,标识符还必须是同一函数的参数;当数组是结构字段时,标识符必须是同一结构的另一个结构字段。

如果在运行时确定任何维度的上限,则数组称为“符合性”。 (只能在 runtime 中确定上限。) 若要确定上限,数组声明必须包含 size_ismax_is 属性。

如果数组的边界在编译时确定,但传输的元素的范围在运行时确定,则称为“变化”。 若要确定传输元素的范围,数组声明必须包含 length_isfirst_islast_is 属性。

一个符合的可变数组 (也称为“open”) 是一个数组,其传输元素的上限和范围是在运行时确定的。 最多可以嵌套在 C 结构中的一个符合性或符合性可变数组,并且必须是结构的最后一个元素。 相比之下,不合格可变数组可能发生在结构中的任何位置。

示例

/* IDL file interface body */ 
#define MAX_INDEX 10 
 
typedef char  ATYPE[MAX_INDEX]; 
typedef short BTYPE[];        // Equivalent to [*]; 
typedef long  CTYPE[*][10];   // [][10] 
typedef float DTYPE[0..10];   // Equivalent to [11] 
typedef float ETYPE[0..(MAX_INDEX)];  
 
typedef struct 
{ 
    unsigned short size; 
    unsigned short length; 
    [size_is(size), length_is(length)] char string[*]; 
} counted_string; 
 
HRESULT MyFunction( 
     [in, out] short * pSize,  
     [in, out, string, size_is(*pSize)] char a[0..*] 
);

有关详细信息,请参阅 数组和指针

多维数组

用户可以声明属于数组的类型,然后声明此类类型的对象的数组。 n 维数组类型的 m 维数组的语义与 m+n 维数组的语义相同。

例如,RECT_TYPE类型可以定义为二维数组,变量 rect 可以定义为RECT_TYPE数组。 这等效于三维数组 equivalent_rect

typedef short int RECT_TYPE[10][20]; 
RECT_TYPE rect[15]; 
short int equivalent_rect[15][10][20];  // ~RECT_TYPE rect[15]

Microsoft RPC 面向 C。 按照 C 语言约定,在运行时只能确定多维数组的第一个维度。 与支持其他语言的 DCE IDL 数组的互操作仅限于:

  • 具有常量 (编译时确定) 边界的多维数组。
  • 具有除第一个维度以外的所有常量边界的多维数组。 第一个维度的传输元素的上限和范围取决于运行时。
  • 下限为零的任何一维数组。

在多维数组上使用 [string] 属性时,该属性将应用于最右侧的数组。

指针数组

引用指针必须指向有效数据。 客户端应用程序必须为 引用指针的 [in][in,out] 数组分配所有内存,尤其是当数组与 [in][in,out][length_is][last_is] 值相关联时。 客户端应用程序还必须在调用之前初始化所有数组元素。 在返回到客户端之前,服务器应用程序必须验证传输范围中的所有数组元素是否都指向有效的存储。

在服务器端,存根为所有数组元素分配存储,而不考虑调用时 [length_is][last_is] 值。 此功能可能会影响应用程序的性能。

对唯一指针的数组没有限制。 在客户端和服务器上,为 null 指针分配存储。 当指针为非 null 时,数据将置于预先分配的存储中。

可选的指针声明符可以位于数组声明符之前。

当嵌入的引用指针是 [out]-only 参数时,服务器管理器代码必须将有效值分配给引用指针数组。 例如:

typedef [ref] short * ARefPointer;
typedef ARefPointer ArrayOfRef[10];
HRESULT proc1( [out] ArrayOfRef Parameter );

生成的存根分配数组,并将 null 值分配给数组中嵌入的所有指针。