Variant Manipulation API Functions
These functions are provided to allow applications to manipulate VARIANTARG variables. Applications that implement IDispatch should test each VARIANTARG for all permitted types by attempting to coerce the variant to each type using VariantChangeType or VariantChangeTypeEx. If objects are allowed, the application should always test for object types before other types. If an object type is expected, the application must use IUnknown::QueryInterface to test whether the object is the desired type.
Although applications can access and interpret the VARIANTARGs without these functions, using them ensures uniform conversion and coercion rules for all implementors of IDispatch. For example, these functions automatically coerce numeric arguments to strings, and vice versa, when necessary.
Because variants can contain strings, references to scalars, objects, and arrays, all data ownership rules must be followed. All variant manipulation functions should conform to the following rules:
-
Before use, all VARIANTARGs must be initialized by VariantInit.
-
For the types VT_UI1, VT_I2, VT_I4, VT_R4, VT_R8, VT_BOOL, VT_ERROR, VT_CY, and VT_DATE, data is stored within the VARIANT structure. Any pointers to the data become invalid when the type of the variant is changed.
-
For VT_BYREF | any type, the memory pointed to by the variant is owned and freed by the caller of the function.
-
For VT_BSTR, there is only one owner for the string. All strings in variants must be allocated with the SysAllocString function. When releasing or changing the type of a variant with the VT_BSTR type, SysFreeString is called on the contained string.
-
For VT_ARRAY | any type, the rule is analogous to the rule for VT_BSTR. All arrays in variants must be allocated with SafeArrayCreate. When releasing or changing the type of a variant with the VT_ARRAY flag set, SafeArrayDestroy is called.
-
For VT_DISPATCH and VT_UNKNOWN, the objects that are pointed to have reference counts that are incremented when they are placed in a variant. When releasing or changing the type of the variant, Release is called on the object that is pointed to.