1// Licensed to the .NET Foundation under one or more agreements.
2// The .NET Foundation licenses this file to you under the MIT license.
3// See the LICENSE file in the project root for more information.
4//
5// File: OleVariant.h
6//
7
8//
9
10
11#ifndef _H_OLEVARIANT_
12#define _H_OLEVARIANT_
13
14
15// The COM interop native array marshaler is built on top of VT_* types.
16// The P/Invoke marshaler supports marshaling to WINBOOL's and ANSICHAR's.
17// This is an annoying workaround to shoehorn these non-OleAut types into
18// the COM interop marshaler.
19#define VTHACK_INSPECTABLE 247
20#define VTHACK_HSTRING 248
21#define VTHACK_REDIRECTEDTYPE 249
22#define VTHACK_CBOOL 250
23#define VTHACK_NONBLITTABLERECORD 251
24#define VTHACK_BLITTABLERECORD 252
25#define VTHACK_ANSICHAR 253
26#define VTHACK_WINBOOL 254
27
28
29//These types must be kept in sync with the CorElementTypes defined in cor.h
30//NOTE: If you add values to this enum you need to look at COMOAVariant.cpp. There is
31// a mapping between CV type and VT types found there.
32//NOTE: This is also found in a table in OleVariant.cpp.
33//NOTE: These are also found in Variant.cs
34typedef enum
35{
36 CV_EMPTY = 0x0, // CV_EMPTY
37 CV_VOID = ELEMENT_TYPE_VOID,
38 CV_BOOLEAN = ELEMENT_TYPE_BOOLEAN,
39 CV_CHAR = ELEMENT_TYPE_CHAR,
40 CV_I1 = ELEMENT_TYPE_I1,
41 CV_U1 = ELEMENT_TYPE_U1,
42 CV_I2 = ELEMENT_TYPE_I2,
43 CV_U2 = ELEMENT_TYPE_U2,
44 CV_I4 = ELEMENT_TYPE_I4,
45 CV_U4 = ELEMENT_TYPE_U4,
46 CV_I8 = ELEMENT_TYPE_I8,
47 CV_U8 = ELEMENT_TYPE_U8,
48 CV_R4 = ELEMENT_TYPE_R4,
49 CV_R8 = ELEMENT_TYPE_R8,
50 CV_STRING = ELEMENT_TYPE_STRING,
51
52 // For the rest, we map directly if it is defined in CorHdr.h and fill
53 // in holes for the rest.
54 CV_PTR = ELEMENT_TYPE_PTR,
55 CV_DATETIME = 0x10, // ELEMENT_TYPE_BYREF
56 CV_TIMESPAN = 0x11, // ELEMENT_TYPE_VALUETYPE
57 CV_OBJECT = ELEMENT_TYPE_CLASS,
58 CV_DECIMAL = 0x13, // ELEMENT_TYPE_UNUSED1
59 CV_CURRENCY = 0x14, // ELEMENT_TYPE_ARRAY
60 CV_ENUM = 0x15, //
61 CV_MISSING = 0x16, //
62 CV_NULL = 0x17, //
63 CV_LAST = 0x18, //
64} CVTypes;
65
66//Mapping from CVType to type handle. Used for conversion between the two internally.
67extern const BinderClassID CVTypeToBinderClassID[];
68
69inline TypeHandle GetTypeHandleForCVType(CVTypes elemType)
70{
71 CONTRACT (TypeHandle)
72 {
73 WRAPPER(THROWS);
74 WRAPPER(GC_TRIGGERS);
75 MODE_ANY;
76 PRECONDITION(elemType < CV_LAST);
77 }
78 CONTRACT_END;
79
80 RETURN TypeHandle(MscorlibBinder::GetClass(CVTypeToBinderClassID[elemType]));
81}
82
83// Use this very carefully. There is not a direct mapping between
84// CorElementType and CVTypes for a bunch of things. In this case
85// we return CV_LAST. You need to check this at the call site.
86extern CVTypes CorElementTypeToCVTypes(CorElementType type);
87
88
89#ifdef FEATURE_COMINTEROP
90
91#include <pshpack1.h>
92
93
94/*** Variant Design Restrictions (ie, decisions we've had to re-do differently):
95 1) A Variant containing all zeros should be a valid Variant of type empty.
96 2) Variant must contain an OBJECTREF field for Objects, etc. Since we
97 have no way of expressing a union between an OBJECTREF and an int, we
98 always box Decimals in a Variant.
99 3) The m_type field is not a CVType and will contain extra bits. People
100 should use VariantData::GetType() to get the CVType.
101 4) You should use SetObjRef and GetObjRef to manipulate the OBJECTREF field.
102 These will handle write barriers correctly, as well as CV_EMPTY.
103
104
105 Empty, Missing & Null:
106 Variants of type CV_EMPTY will be all zero's. This forces us to add in
107 special cases for all functions that convert a Variant into an object (such
108 as copying a Variant into an Object[]).
109
110 Variants of type Missing and Null will have their objectref field set to
111 Missing.Value and Null.Value respectively. This simplifies the code in
112 Variant.cs and strewn throughout the EE.
113*/
114
115#define VARIANT_TYPE_MASK 0xFFFF
116#define VT_MASK 0xFF000000
117#define VT_BITSHIFT 24
118
119struct VariantData
120{
121public:
122 static void NewVariant(VariantData * const& dest, const CVTypes type, INT64 data
123 DEBUG_ARG(BOOL bDestIsInterior = FALSE));
124
125 FORCEINLINE CVTypes GetType() const
126 {
127 LIMITED_METHOD_CONTRACT;
128
129 return (CVTypes)(m_type & VARIANT_TYPE_MASK);
130 }
131
132 FORCEINLINE void SetType(INT32 in)
133 {
134 LIMITED_METHOD_CONTRACT;
135 m_type = in;
136 }
137
138 FORCEINLINE VARTYPE GetVT() const
139 {
140 LIMITED_METHOD_CONTRACT;
141
142 VARTYPE vt = (m_type & VT_MASK) >> VT_BITSHIFT;
143 if (vt & 0x80)
144 {
145 vt &= ~0x80;
146 vt |= VT_ARRAY;
147 }
148 return vt;
149 }
150
151 FORCEINLINE void SetVT(VARTYPE vt)
152 {
153 CONTRACTL
154 {
155 NOTHROW;
156 GC_NOTRIGGER;
157 MODE_ANY;
158 PRECONDITION( !(vt & VT_BYREF) );
159 PRECONDITION( (vt & ~VT_ARRAY) < 128 );
160 }
161 CONTRACTL_END;
162
163 if (vt & VT_ARRAY)
164 {
165 vt &= ~VT_ARRAY;
166 vt |= 0x80;
167 }
168 m_type = (m_type & ~((INT32)VT_MASK)) | (vt << VT_BITSHIFT);
169 }
170
171
172 FORCEINLINE OBJECTREF GetObjRef() const
173 {
174 WRAPPER_NO_CONTRACT;
175
176 return (OBJECTREF)m_or;
177 }
178
179 OBJECTREF* GetObjRefPtr()
180 {
181 CONTRACT (OBJECTREF*)
182 {
183 NOTHROW;
184 GC_NOTRIGGER;
185 MODE_COOPERATIVE;
186 POSTCONDITION(CheckPointer(RETVAL, NULL_OK));
187 }
188 CONTRACT_END;
189
190 RETURN (OBJECTREF*)&m_or;
191 }
192
193 void SetObjRef(OBJECTREF objRef)
194 {
195 CONTRACTL
196 {
197 NOTHROW;
198 GC_NOTRIGGER;
199 MODE_COOPERATIVE;
200 }
201 CONTRACTL_END;
202
203 if (objRef!=NULL)
204 {
205 SetObjectReferenceUnchecked((OBJECTREF*)&m_or, objRef);
206 }
207 else
208 {
209 // Casting trick to avoid going thru overloaded operator= (which
210 // in this case would trigger a false write barrier violation assert.)
211 *(LPVOID*)(OBJECTREF*)&m_or=NULL;
212 }
213 }
214
215 FORCEINLINE void* GetData() const
216 {
217 LIMITED_METHOD_CONTRACT;
218 return (void *)(&m_data);
219 }
220
221 FORCEINLINE INT8 GetDataAsInt8() const
222 {
223 LIMITED_METHOD_CONTRACT;
224 return (INT8)m_data;
225 }
226
227 FORCEINLINE UINT8 GetDataAsUInt8() const
228 {
229 LIMITED_METHOD_CONTRACT;
230 return (UINT8)m_data;
231 }
232
233 FORCEINLINE INT16 GetDataAsInt16() const
234 {
235 LIMITED_METHOD_CONTRACT;
236 return (INT16)m_data;
237 }
238
239 FORCEINLINE UINT16 GetDataAsUInt16() const
240 {
241 LIMITED_METHOD_CONTRACT;
242 return (UINT16)m_data;
243 }
244
245 FORCEINLINE INT32 GetDataAsInt32() const
246 {
247 LIMITED_METHOD_CONTRACT;
248 return (INT32)m_data;
249 }
250
251 FORCEINLINE UINT32 GetDataAsUInt32() const
252 {
253 LIMITED_METHOD_CONTRACT;
254 return (UINT32)m_data;
255 }
256
257 FORCEINLINE INT64 GetDataAsInt64() const
258 {
259 LIMITED_METHOD_CONTRACT;
260 return (INT64)m_data;
261 }
262
263 FORCEINLINE UINT64 GetDataAsUInt64() const
264 {
265 LIMITED_METHOD_CONTRACT;
266 return (UINT64)m_data;
267 }
268
269 FORCEINLINE void SetData(void *in)
270 {
271 LIMITED_METHOD_CONTRACT;
272
273 if (!in)
274 m_data=0;
275 else
276 m_data = *(INT64 *)in;
277 }
278
279 // When possible, please use the most specific SetDataAsXxx function.
280 // This is necessary to guarantee we do sign extension correctly
281 // for all types smaller than 32 bits. R4's, R8's, U8's, DateTimes,
282 // Currencies, and TimeSpans can all be treated as ints of the appropriate
283 // size - sign extension is irrelevant in those cases.
284 FORCEINLINE void SetDataAsInt8(INT8 data)
285 {
286 LIMITED_METHOD_CONTRACT;
287 m_data=data;
288 }
289
290 FORCEINLINE void SetDataAsUInt8(UINT8 data)
291 {
292 LIMITED_METHOD_CONTRACT;
293 m_data=data;
294 }
295
296 FORCEINLINE void SetDataAsInt16(INT16 data)
297 {
298 LIMITED_METHOD_CONTRACT;
299 m_data=data;
300 }
301
302 FORCEINLINE void SetDataAsUInt16(UINT16 data)
303 {
304 LIMITED_METHOD_CONTRACT;
305 m_data=data;
306 }
307
308 FORCEINLINE void SetDataAsInt32(INT32 data)
309 {
310 LIMITED_METHOD_CONTRACT;
311 m_data=data;
312 }
313
314 FORCEINLINE void SetDataAsUInt32(UINT32 data)
315 {
316 LIMITED_METHOD_CONTRACT;
317 m_data=data;
318 }
319
320 FORCEINLINE void SetDataAsInt64(INT64 data)
321 {
322 LIMITED_METHOD_CONTRACT;
323 m_data=data;
324 }
325
326private:
327 Object* m_or;
328 INT64 m_data;
329 INT32 m_type;
330};
331
332#include <poppack.h>
333
334#endif // FEATURE_COMINTEROP
335
336
337class OleVariant
338{
339 public:
340
341#ifdef FEATURE_COMINTEROP
342 // New variant conversion
343 static void MarshalOleVariantForObject(OBJECTREF * const & pObj, VARIANT *pOle);
344 static void MarshalObjectForOleVariant(const VARIANT *pOle, OBJECTREF * const & pObj);
345 static void MarshalOleRefVariantForObject(OBJECTREF *pObj, VARIANT *pOle);
346
347 // Helper functions to convert BSTR to managed strings.
348 static void AllocateEmptyStringForBSTR(BSTR bstr, STRINGREF *pStringObj);
349 static void ConvertContentsBSTRToString(BSTR bstr, STRINGREF *pStringObj);
350 static void ConvertBSTRToString(BSTR bstr, STRINGREF *pStringObj);
351
352 // Helper functions to convert managed strings to BSTRs.
353 static BSTR AllocateEmptyBSTRForString(STRINGREF *pStringObj);
354 static void ConvertContentsStringToBSTR(STRINGREF *pStringObj, BSTR bstr);
355 static BSTR ConvertStringToBSTR(STRINGREF *pStringObj);
356 static void MarshalComVariantForOleVariant(VARIANT *pOle, VariantData *pCom);
357 static void MarshalOleVariantForComVariant(VariantData *pCom, VARIANT *pOle);
358#endif // FEATURE_COMINTEROP
359
360#ifdef FEATURE_COMINTEROP
361 // Safearray conversion
362
363 static SAFEARRAY* CreateSafeArrayDescriptorForArrayRef(BASEARRAYREF* pArrayRef, VARTYPE vt,
364 MethodTable* pInterfaceMT = NULL);
365
366 static SAFEARRAY* CreateSafeArrayForArrayRef(BASEARRAYREF* pArrayRef, VARTYPE vt,
367 MethodTable* pInterfaceMT = NULL);
368
369 static BASEARRAYREF CreateArrayRefForSafeArray(SAFEARRAY* pSafeArray, VARTYPE vt,
370 MethodTable* pElementMT);
371
372 static void MarshalSafeArrayForArrayRef(BASEARRAYREF* pArrayRef,
373 SAFEARRAY* pSafeArray,
374 VARTYPE vt,
375 MethodTable* pInterfaceMT,
376 BOOL fSafeArrayIsValid = TRUE);
377
378 static void MarshalArrayRefForSafeArray(SAFEARRAY* pSafeArray,
379 BASEARRAYREF* pArrayRef,
380 VARTYPE vt,
381 MethodTable* pInterfaceMT);
382
383 // Helper function to convert a boxed value class to an OLE variant.
384 static void ConvertValueClassToVariant(OBJECTREF *pBoxedValueClass, VARIANT *pOleVariant);
385
386 // Helper function to transpose the data in a multidimensionnal array.
387 static void TransposeArrayData(BYTE *pDestData, BYTE *pSrcData, SIZE_T dwNumComponents, SIZE_T dwComponentSize, SAFEARRAY *pSafeArray, BOOL bSafeArrayToMngArray);
388
389 // Helper to determine if an array is an array of wrappers.
390 static BOOL IsArrayOfWrappers(BASEARRAYREF *pArray, BOOL *pbOfInterfaceWrappers);
391
392 // Helper to extract the wrapped objects from an array.
393 static BASEARRAYREF ExtractWrappedObjectsFromArray(BASEARRAYREF *pArray);
394
395 static HRESULT ClearAndInsertContentsIntoByrefRecordVariant(VARIANT* pOle, OBJECTREF* pObj);
396
397 static BOOL IsValidArrayForSafeArrayElementType(BASEARRAYREF* pArrayRef, VARTYPE vtExpected);
398#endif // FEATURE_COMINTEROP
399
400#ifdef FEATURE_COMINTEROP
401 static BOOL CheckVariant(VARIANT *pOle);
402
403 // Type conversion utilities
404 static void ExtractContentsFromByrefVariant(VARIANT* pByrefVar, VARIANT* pDestVar);
405 static void InsertContentsIntoByrefVariant(VARIANT* pSrcVar, VARIANT* pByrefVar);
406 static void CreateByrefVariantForVariant(VARIANT* pSrcVar, VARIANT* pByrefVar);
407
408 static VARTYPE GetVarTypeForComVariant(VariantData* pComVariant);
409#endif // FEATURE_COMINTEROP
410
411 static CVTypes GetCVTypeForVarType(VARTYPE vt);
412 static VARTYPE GetVarTypeForCVType(CVTypes);
413 static VARTYPE GetVarTypeForTypeHandle(TypeHandle typeHnd);
414
415 static VARTYPE GetVarTypeForValueClassArrayName(LPCUTF8 pArrayClassName);
416 static VARTYPE GetElementVarTypeForArrayRef(BASEARRAYREF pArrayRef);
417
418 // Note that Rank == 0 means SZARRAY (that is rank 1, no lower bounds)
419 static TypeHandle GetArrayForVarType(VARTYPE vt, TypeHandle elemType, unsigned rank=0);
420 static UINT GetElementSizeForVarType(VARTYPE vt, MethodTable* pInterfaceMT);
421
422#ifdef FEATURE_COMINTEROP
423 // Determine the element type of the objects being wrapped by an array of wrappers.
424 static TypeHandle GetWrappedArrayElementType(BASEARRAYREF* pArray);
425
426 // Determines the element type of an array taking wrappers into account. This means
427 // that is an array of wrappers is passed in, the returned element type will be that
428 // of the wrapped objects, not of the wrappers.
429 static TypeHandle GetArrayElementTypeWrapperAware(BASEARRAYREF* pArray);
430
431 // Determine the type of the elements for a safe array of records.
432 static TypeHandle GetElementTypeForRecordSafeArray(SAFEARRAY* pSafeArray);
433
434 // Helper called from MarshalIUnknownArrayComToOle and MarshalIDispatchArrayComToOle.
435 static void MarshalInterfaceArrayComToOleHelper(BASEARRAYREF* pComArray, void* oleArray,
436 MethodTable* pElementMT, BOOL bDefaultIsDispatch,
437 SIZE_T cElements);
438#endif // FEATURE_COMINTEROP
439
440 struct Marshaler
441 {
442#ifdef FEATURE_COMINTEROP
443 void (*OleToComVariant)(VARIANT* pOleVariant, VariantData* pComVariant);
444 void (*ComToOleVariant)(VariantData* pComVariant, VARIANT* pOleVariant);
445 void (*OleRefToComVariant)(VARIANT* pOleVariant, VariantData* pComVariant);
446#endif // FEATURE_COMINTEROP
447 void (*OleToComArray)(void* oleArray, BASEARRAYREF* pComArray, MethodTable* pInterfaceMT);
448 void (*ComToOleArray)(BASEARRAYREF* pComArray, void* oleArray, MethodTable* pInterfaceMT,
449 BOOL fBestFitMapping, BOOL fThrowOnUnmappableChar,
450 BOOL fOleArrayIsValid,SIZE_T cElements);
451 void (*ClearOleArray)(void* oleArray, SIZE_T cElements, MethodTable* pInterfaceMT);
452 };
453
454 static const Marshaler* GetMarshalerForVarType(VARTYPE vt, BOOL fThrow);
455
456 static void MarshalVariantArrayComToOle(BASEARRAYREF* pComArray, void* oleArray,
457 MethodTable* pInterfaceMT, BOOL fBestFitMapping,
458 BOOL fThrowOnUnmappableChar, BOOL fMarshalByrefArgOnly,
459 BOOL fOleArrayIsValid, int nOleArrayStepLength = 1);
460
461private:
462
463
464 // Specific marshaler functions
465
466 static void MarshalBoolArrayOleToCom(void *oleArray, BASEARRAYREF* pComArray,
467 MethodTable* pInterfaceMT);
468 static void MarshalBoolArrayComToOle(BASEARRAYREF* pComArray, void* oleArray,
469 MethodTable* pInterfaceMT, BOOL fBestFitMapping,
470 BOOL fThrowOnUnmappableChar, BOOL fOleArrayIsValid,
471 SIZE_T cElements);
472
473 static void MarshalWinBoolArrayOleToCom(void* oleArray, BASEARRAYREF* pComArray,
474 MethodTable* pInterfaceMT);
475 static void MarshalWinBoolArrayComToOle(BASEARRAYREF* pComArray, void* oleArray,
476 MethodTable* pInterfaceMT, BOOL fBestFitMapping,
477 BOOL fThrowOnUnmappableChar, BOOL fOleArrayValid,
478 SIZE_T cElements);
479 static void MarshalCBoolVariantOleToCom(VARIANT* pOleVariant, VariantData* pComVariant);
480 static void MarshalCBoolVariantComToOle(VariantData* pComVariant, VARIANT* pOleVariant);
481 static void MarshalCBoolVariantOleRefToCom(VARIANT* pOleVariant, VariantData* pComVariant);
482 static void MarshalCBoolArrayOleToCom(void* oleArray, BASEARRAYREF* pComArray,
483 MethodTable* pInterfaceMT);
484 static void MarshalCBoolArrayComToOle(BASEARRAYREF* pComArray, void* oleArray,
485 MethodTable* pInterfaceMT, BOOL fBestFitMapping,
486 BOOL fThrowOnUnmappableChar, BOOL fOleArrayValid,
487 SIZE_T cElements);
488
489 static void MarshalAnsiCharArrayOleToCom(void* oleArray, BASEARRAYREF* pComArray,
490 MethodTable* pInterfaceMT);
491 static void MarshalAnsiCharArrayComToOle(BASEARRAYREF* pComArray, void* oleArray,
492 MethodTable* pInterfaceMT, BOOL fBestFitMapping,
493 BOOL fThrowOnUnmappableChar, BOOL fOleArrayValid,
494 SIZE_T cElements);
495
496#ifdef FEATURE_COMINTEROP
497 static void MarshalIDispatchArrayComToOle(BASEARRAYREF* pComArray, void* oleArray,
498 MethodTable* pInterfaceMT, BOOL fBestFitMapping,
499 BOOL fThrowOnUnmappableChar, BOOL fOleArrayValid,
500 SIZE_T cElements);
501#endif // FEATURE_COMINTEROP
502
503#ifdef FEATURE_COMINTEROP
504 static void MarshalBSTRArrayOleToCom(void* oleArray, BASEARRAYREF* pComArray,
505 MethodTable* pInterfaceMT);
506 static void MarshalBSTRArrayComToOle(BASEARRAYREF* pComArray, void* oleArray,
507 MethodTable* pInterfaceMT, BOOL fBestFitMapping,
508 BOOL fThrowOnUnmappableChar, BOOL fOleArrayValid,
509 SIZE_T cElements);
510 static void ClearBSTRArray(void* oleArray, SIZE_T cElements, MethodTable* pInterfaceMT);
511#endif // FEATURE_COMINTEROP
512
513 static void MarshalNonBlittableRecordArrayOleToCom(void* oleArray, BASEARRAYREF* pComArray,
514 MethodTable* pInterfaceMT);
515 static void MarshalNonBlittableRecordArrayComToOle(BASEARRAYREF* pComArray, void* oleArray,
516 MethodTable* pInterfaceMT, BOOL fBestFitMapping,
517 BOOL fThrowOnUnmappableChar, BOOL fOleArrayValid,
518 SIZE_T cElements);
519 static void ClearNonBlittableRecordArray(void* oleArray, SIZE_T cElements, MethodTable* pInterfaceMT);
520
521 static void MarshalLPWSTRArrayOleToCom(void* oleArray, BASEARRAYREF* pComArray,
522 MethodTable* pInterfaceMT);
523 static void MarshalLPWSTRRArrayComToOle(BASEARRAYREF* pComArray, void* oleArray,
524 MethodTable* pInterfaceMT, BOOL fBestFitMapping,
525 BOOL fThrowOnUnmappableChar, BOOL fOleArrayValid,
526 SIZE_T cElements);
527 static void ClearLPWSTRArray(void* oleArray, SIZE_T cElements, MethodTable* pInterfaceMT);
528
529 static void MarshalLPSTRArrayOleToCom(void* oleArray, BASEARRAYREF* pComArray,
530 MethodTable* pInterfaceMT);
531 static void MarshalLPSTRRArrayComToOle(BASEARRAYREF* pComArray, void* oleArray,
532 MethodTable* pInterfaceMT, BOOL fBestFitMapping,
533 BOOL fThrowOnUnmappableChar, BOOL fOleArrayValid,
534 SIZE_T cElements);
535 static void ClearLPSTRArray(void* oleArray, SIZE_T cElements, MethodTable* pInterfaceMT);
536
537 static void MarshalDateArrayOleToCom(void* oleArray, BASEARRAYREF* pComArray,
538 MethodTable* pInterfaceMT);
539 static void MarshalDateArrayComToOle(BASEARRAYREF* pComArray, void* oleArray,
540 MethodTable* pInterfaceMT, BOOL fBestFitMapping,
541 BOOL fThrowOnUnmappableChar, BOOL fOleArrayValid,
542 SIZE_T cElements);
543
544 static void MarshalRecordArrayOleToCom(void* oleArray, BASEARRAYREF* pComArray, MethodTable* pElementMT);
545 static void MarshalRecordArrayComToOle(BASEARRAYREF* pComArray, void* oleArray, MethodTable* pElementMT,
546 BOOL fBestFitMapping, BOOL fThrowOnUnmappableChar,
547 BOOL fOleArrayValid,
548 SIZE_T cElements);
549 static void ClearRecordArray(void* oleArray, SIZE_T cElements, MethodTable* pElementMT);
550
551#ifdef FEATURE_COMINTEROP
552 static HRESULT MarshalCommonOleRefVariantForObject(OBJECTREF *pObj, VARIANT *pOle);
553 static void MarshalInterfaceArrayOleToCom(void* oleArray, BASEARRAYREF* pComArray,
554 MethodTable* pInterfaceMT);
555 static void MarshalIUnknownArrayComToOle(BASEARRAYREF* pComArray, void* oleArray,
556 MethodTable* pInterfaceMT, BOOL fBestFitMapping,
557 BOOL fThrowOnUnmappableChar, BOOL fOleArrayValid,
558 SIZE_T cElements);
559 static void ClearInterfaceArray(void* oleArray, SIZE_T cElements, MethodTable* pInterfaceMT);
560
561 static void MarshalBoolVariantOleToCom(VARIANT* pOleVariant, VariantData* pComVariant);
562
563 static void MarshalWinBoolVariantOleToCom(VARIANT* pOleVariant, VariantData* pComVariant);
564 static void MarshalWinBoolVariantComToOle(VariantData* pComVariant, VARIANT* pOleVariant);
565 static void MarshalWinBoolVariantOleRefToCom(VARIANT* pOleVariant, VariantData* pComVariant);
566
567 static void MarshalAnsiCharVariantOleToCom(VARIANT* pOleVariant, VariantData* pComVariant);
568 static void MarshalAnsiCharVariantComToOle(VariantData* pComVariant, VARIANT* pOleVariant);
569 static void MarshalAnsiCharVariantOleRefToCom(VARIANT* pOleVariant, VariantData* pComVariant);
570
571 static void MarshalInterfaceVariantOleToCom(VARIANT* pOleVariant, VariantData* pComVariant);
572 static void MarshalInterfaceVariantComToOle(VariantData* pComVariant, VARIANT* pOleVariant);
573 static void MarshalInterfaceVariantOleRefToCom(VARIANT* pOleVariant, VariantData* pComVariant);
574
575 static void MarshalBSTRVariantOleToCom(VARIANT* pOleVariant, VariantData* pComVariant);
576 static void MarshalBSTRVariantComToOle(VariantData* pComVariant, VARIANT* pOleVariant);
577
578 static void MarshalDateVariantOleToCom(VARIANT* pOleVariant, VariantData* pComVariant);
579 static void MarshalDateVariantComToOle(VariantData* pComVariant, VARIANT* pOleVariant);
580 static void MarshalDateVariantOleRefToCom(VARIANT* pOleVariant, VariantData* pComVariant);
581
582 static void MarshalDecimalVariantOleToCom(VARIANT* pOleVariant, VariantData* pComVariant);
583 static void MarshalDecimalVariantComToOle(VariantData* pComVariant, VARIANT* pOleVariant);
584 static void MarshalDecimalVariantOleRefToCom(VARIANT* pOleVariant, VariantData* pComVariant);
585
586#ifdef FEATURE_CLASSIC_COMINTEROP
587 static void MarshalRecordVariantOleToCom(VARIANT* pOleVariant, VariantData* pComVariant);
588 static void MarshalRecordVariantComToOle(VariantData* pComVariant, VARIANT* pOleVariant);
589 static void MarshalRecordVariantOleRefToCom(VARIANT* pOleVariant, VariantData* pComVariant);
590#endif
591
592 static void MarshalCurrencyVariantOleToCom(VARIANT* pOleVariant, VariantData* pComVariant);
593 static void MarshalCurrencyVariantComToOle(VariantData* pComVariant, VARIANT* pOleVariant);
594 static void MarshalCurrencyVariantOleRefToCom(VARIANT* pOleVariant, VariantData* pComVariant);
595 static void MarshalCurrencyArrayOleToCom(void* oleArray, BASEARRAYREF* pComArray,
596 MethodTable* pInterfaceMT);
597 static void MarshalCurrencyArrayComToOle(BASEARRAYREF* pComArray, void* oleArray,
598 MethodTable* pInterfaceMT, BOOL fBestFitMapping,
599 BOOL fThrowOnUnmappableChar, BOOL fOleArrayValid,
600 SIZE_T cElements);
601
602 static void MarshalVariantArrayOleToCom(void* oleArray, BASEARRAYREF* pComArray,
603 MethodTable* pInterfaceMT);
604 static void MarshalVariantArrayComToOle(BASEARRAYREF* pComArray, void* oleArray,
605 MethodTable* pInterfaceMT, BOOL fBestFitMapping,
606 BOOL fThrowOnUnmappableChar, BOOL fOleArrayValid,
607 SIZE_T cElements);
608 static void ClearVariantArray(void* oleArray, SIZE_T cElements, MethodTable* pInterfaceMT);
609
610#ifdef FEATURE_CLASSIC_COMINTEROP
611 static void MarshalArrayVariantOleToCom(VARIANT* pOleVariant, VariantData* pComVariant);
612 static void MarshalArrayVariantComToOle(VariantData* pComVariant, VARIANT* pOleVariant);
613 static void MarshalArrayVariantOleRefToCom(VARIANT* pOleVariant, VariantData* pComVariant);
614#endif
615
616 static void MarshalErrorVariantOleToCom(VARIANT* pOleVariant, VariantData* pComVariant);
617 static void MarshalErrorVariantOleRefToCom(VARIANT* pOleVariant, VariantData* pComVariant);
618 static void MarshalErrorVariantComToOle(VariantData* pComVariant, VARIANT* pOleVariant);
619#endif // FEATURE_COMINTEROP
620};
621
622#endif
623