1*f6dc9357SAndroid Build Coastguard Worker // Windows/PropVariant.cpp
2*f6dc9357SAndroid Build Coastguard Worker
3*f6dc9357SAndroid Build Coastguard Worker #include "StdAfx.h"
4*f6dc9357SAndroid Build Coastguard Worker
5*f6dc9357SAndroid Build Coastguard Worker #include "../Common/Defs.h"
6*f6dc9357SAndroid Build Coastguard Worker
7*f6dc9357SAndroid Build Coastguard Worker #include "PropVariant.h"
8*f6dc9357SAndroid Build Coastguard Worker
9*f6dc9357SAndroid Build Coastguard Worker namespace NWindows {
10*f6dc9357SAndroid Build Coastguard Worker namespace NCOM {
11*f6dc9357SAndroid Build Coastguard Worker
AllocBstrFromAscii(const char * s)12*f6dc9357SAndroid Build Coastguard Worker BSTR AllocBstrFromAscii(const char *s) throw()
13*f6dc9357SAndroid Build Coastguard Worker {
14*f6dc9357SAndroid Build Coastguard Worker if (!s)
15*f6dc9357SAndroid Build Coastguard Worker return NULL;
16*f6dc9357SAndroid Build Coastguard Worker UINT len = (UINT)strlen(s);
17*f6dc9357SAndroid Build Coastguard Worker BSTR p = ::SysAllocStringLen(NULL, len);
18*f6dc9357SAndroid Build Coastguard Worker if (p)
19*f6dc9357SAndroid Build Coastguard Worker {
20*f6dc9357SAndroid Build Coastguard Worker for (UINT i = 0; i <= len; i++)
21*f6dc9357SAndroid Build Coastguard Worker p[i] = (Byte)s[i];
22*f6dc9357SAndroid Build Coastguard Worker }
23*f6dc9357SAndroid Build Coastguard Worker return p;
24*f6dc9357SAndroid Build Coastguard Worker }
25*f6dc9357SAndroid Build Coastguard Worker
PropVarEm_Alloc_Bstr(PROPVARIANT * p,unsigned numChars)26*f6dc9357SAndroid Build Coastguard Worker HRESULT PropVarEm_Alloc_Bstr(PROPVARIANT *p, unsigned numChars) throw()
27*f6dc9357SAndroid Build Coastguard Worker {
28*f6dc9357SAndroid Build Coastguard Worker p->bstrVal = ::SysAllocStringLen(NULL, numChars);
29*f6dc9357SAndroid Build Coastguard Worker if (!p->bstrVal)
30*f6dc9357SAndroid Build Coastguard Worker {
31*f6dc9357SAndroid Build Coastguard Worker p->vt = VT_ERROR;
32*f6dc9357SAndroid Build Coastguard Worker p->scode = E_OUTOFMEMORY;
33*f6dc9357SAndroid Build Coastguard Worker return E_OUTOFMEMORY;
34*f6dc9357SAndroid Build Coastguard Worker }
35*f6dc9357SAndroid Build Coastguard Worker p->vt = VT_BSTR;
36*f6dc9357SAndroid Build Coastguard Worker return S_OK;
37*f6dc9357SAndroid Build Coastguard Worker }
38*f6dc9357SAndroid Build Coastguard Worker
PropVarEm_Set_Str(PROPVARIANT * p,const char * s)39*f6dc9357SAndroid Build Coastguard Worker HRESULT PropVarEm_Set_Str(PROPVARIANT *p, const char *s) throw()
40*f6dc9357SAndroid Build Coastguard Worker {
41*f6dc9357SAndroid Build Coastguard Worker p->bstrVal = AllocBstrFromAscii(s);
42*f6dc9357SAndroid Build Coastguard Worker if (p->bstrVal)
43*f6dc9357SAndroid Build Coastguard Worker {
44*f6dc9357SAndroid Build Coastguard Worker p->vt = VT_BSTR;
45*f6dc9357SAndroid Build Coastguard Worker return S_OK;
46*f6dc9357SAndroid Build Coastguard Worker }
47*f6dc9357SAndroid Build Coastguard Worker p->vt = VT_ERROR;
48*f6dc9357SAndroid Build Coastguard Worker p->scode = E_OUTOFMEMORY;
49*f6dc9357SAndroid Build Coastguard Worker return E_OUTOFMEMORY;
50*f6dc9357SAndroid Build Coastguard Worker }
51*f6dc9357SAndroid Build Coastguard Worker
CPropVariant(const PROPVARIANT & varSrc)52*f6dc9357SAndroid Build Coastguard Worker CPropVariant::CPropVariant(const PROPVARIANT &varSrc)
53*f6dc9357SAndroid Build Coastguard Worker {
54*f6dc9357SAndroid Build Coastguard Worker vt = VT_EMPTY;
55*f6dc9357SAndroid Build Coastguard Worker InternalCopy(&varSrc);
56*f6dc9357SAndroid Build Coastguard Worker }
57*f6dc9357SAndroid Build Coastguard Worker
CPropVariant(const CPropVariant & varSrc)58*f6dc9357SAndroid Build Coastguard Worker CPropVariant::CPropVariant(const CPropVariant &varSrc)
59*f6dc9357SAndroid Build Coastguard Worker {
60*f6dc9357SAndroid Build Coastguard Worker vt = VT_EMPTY;
61*f6dc9357SAndroid Build Coastguard Worker InternalCopy(&varSrc);
62*f6dc9357SAndroid Build Coastguard Worker }
63*f6dc9357SAndroid Build Coastguard Worker
CPropVariant(BSTR bstrSrc)64*f6dc9357SAndroid Build Coastguard Worker CPropVariant::CPropVariant(BSTR bstrSrc)
65*f6dc9357SAndroid Build Coastguard Worker {
66*f6dc9357SAndroid Build Coastguard Worker vt = VT_EMPTY;
67*f6dc9357SAndroid Build Coastguard Worker *this = bstrSrc;
68*f6dc9357SAndroid Build Coastguard Worker }
69*f6dc9357SAndroid Build Coastguard Worker
CPropVariant(LPCOLESTR lpszSrc)70*f6dc9357SAndroid Build Coastguard Worker CPropVariant::CPropVariant(LPCOLESTR lpszSrc)
71*f6dc9357SAndroid Build Coastguard Worker {
72*f6dc9357SAndroid Build Coastguard Worker vt = VT_EMPTY;
73*f6dc9357SAndroid Build Coastguard Worker *this = lpszSrc;
74*f6dc9357SAndroid Build Coastguard Worker }
75*f6dc9357SAndroid Build Coastguard Worker
operator =(const CPropVariant & varSrc)76*f6dc9357SAndroid Build Coastguard Worker CPropVariant& CPropVariant::operator=(const CPropVariant &varSrc)
77*f6dc9357SAndroid Build Coastguard Worker {
78*f6dc9357SAndroid Build Coastguard Worker InternalCopy(&varSrc);
79*f6dc9357SAndroid Build Coastguard Worker return *this;
80*f6dc9357SAndroid Build Coastguard Worker }
81*f6dc9357SAndroid Build Coastguard Worker
operator =(const PROPVARIANT & varSrc)82*f6dc9357SAndroid Build Coastguard Worker CPropVariant& CPropVariant::operator=(const PROPVARIANT &varSrc)
83*f6dc9357SAndroid Build Coastguard Worker {
84*f6dc9357SAndroid Build Coastguard Worker InternalCopy(&varSrc);
85*f6dc9357SAndroid Build Coastguard Worker return *this;
86*f6dc9357SAndroid Build Coastguard Worker }
87*f6dc9357SAndroid Build Coastguard Worker
operator =(BSTR bstrSrc)88*f6dc9357SAndroid Build Coastguard Worker CPropVariant& CPropVariant::operator=(BSTR bstrSrc)
89*f6dc9357SAndroid Build Coastguard Worker {
90*f6dc9357SAndroid Build Coastguard Worker *this = (LPCOLESTR)bstrSrc;
91*f6dc9357SAndroid Build Coastguard Worker return *this;
92*f6dc9357SAndroid Build Coastguard Worker }
93*f6dc9357SAndroid Build Coastguard Worker
94*f6dc9357SAndroid Build Coastguard Worker static const char * const kMemException = "out of memory";
95*f6dc9357SAndroid Build Coastguard Worker
operator =(LPCOLESTR lpszSrc)96*f6dc9357SAndroid Build Coastguard Worker CPropVariant& CPropVariant::operator=(LPCOLESTR lpszSrc)
97*f6dc9357SAndroid Build Coastguard Worker {
98*f6dc9357SAndroid Build Coastguard Worker InternalClear();
99*f6dc9357SAndroid Build Coastguard Worker vt = VT_BSTR;
100*f6dc9357SAndroid Build Coastguard Worker wReserved1 = 0;
101*f6dc9357SAndroid Build Coastguard Worker bstrVal = ::SysAllocString(lpszSrc);
102*f6dc9357SAndroid Build Coastguard Worker if (!bstrVal && lpszSrc)
103*f6dc9357SAndroid Build Coastguard Worker {
104*f6dc9357SAndroid Build Coastguard Worker throw kMemException;
105*f6dc9357SAndroid Build Coastguard Worker // vt = VT_ERROR;
106*f6dc9357SAndroid Build Coastguard Worker // scode = E_OUTOFMEMORY;
107*f6dc9357SAndroid Build Coastguard Worker }
108*f6dc9357SAndroid Build Coastguard Worker return *this;
109*f6dc9357SAndroid Build Coastguard Worker }
110*f6dc9357SAndroid Build Coastguard Worker
operator =(const UString & s)111*f6dc9357SAndroid Build Coastguard Worker CPropVariant& CPropVariant::operator=(const UString &s)
112*f6dc9357SAndroid Build Coastguard Worker {
113*f6dc9357SAndroid Build Coastguard Worker InternalClear();
114*f6dc9357SAndroid Build Coastguard Worker vt = VT_BSTR;
115*f6dc9357SAndroid Build Coastguard Worker wReserved1 = 0;
116*f6dc9357SAndroid Build Coastguard Worker bstrVal = ::SysAllocStringLen(s, s.Len());
117*f6dc9357SAndroid Build Coastguard Worker if (!bstrVal)
118*f6dc9357SAndroid Build Coastguard Worker throw kMemException;
119*f6dc9357SAndroid Build Coastguard Worker return *this;
120*f6dc9357SAndroid Build Coastguard Worker }
121*f6dc9357SAndroid Build Coastguard Worker
operator =(const UString2 & s)122*f6dc9357SAndroid Build Coastguard Worker CPropVariant& CPropVariant::operator=(const UString2 &s)
123*f6dc9357SAndroid Build Coastguard Worker {
124*f6dc9357SAndroid Build Coastguard Worker /*
125*f6dc9357SAndroid Build Coastguard Worker if (s.IsEmpty())
126*f6dc9357SAndroid Build Coastguard Worker *this = L"";
127*f6dc9357SAndroid Build Coastguard Worker else
128*f6dc9357SAndroid Build Coastguard Worker */
129*f6dc9357SAndroid Build Coastguard Worker {
130*f6dc9357SAndroid Build Coastguard Worker InternalClear();
131*f6dc9357SAndroid Build Coastguard Worker vt = VT_BSTR;
132*f6dc9357SAndroid Build Coastguard Worker wReserved1 = 0;
133*f6dc9357SAndroid Build Coastguard Worker bstrVal = ::SysAllocStringLen(s.GetRawPtr(), s.Len());
134*f6dc9357SAndroid Build Coastguard Worker if (!bstrVal)
135*f6dc9357SAndroid Build Coastguard Worker throw kMemException;
136*f6dc9357SAndroid Build Coastguard Worker /* SysAllocStringLen probably appends a null-terminating character for NULL string.
137*f6dc9357SAndroid Build Coastguard Worker But it doesn't specified in MSDN.
138*f6dc9357SAndroid Build Coastguard Worker But we suppose that it works
139*f6dc9357SAndroid Build Coastguard Worker
140*f6dc9357SAndroid Build Coastguard Worker if (!s.GetRawPtr())
141*f6dc9357SAndroid Build Coastguard Worker {
142*f6dc9357SAndroid Build Coastguard Worker *bstrVal = 0;
143*f6dc9357SAndroid Build Coastguard Worker }
144*f6dc9357SAndroid Build Coastguard Worker */
145*f6dc9357SAndroid Build Coastguard Worker
146*f6dc9357SAndroid Build Coastguard Worker /* MSDN: Windows CE: SysAllocStringLen() : Passing invalid (and under some circumstances NULL)
147*f6dc9357SAndroid Build Coastguard Worker pointers to this function causes an unexpected termination of the application.
148*f6dc9357SAndroid Build Coastguard Worker Is it safe? Maybe we must chamnge the code for that case ? */
149*f6dc9357SAndroid Build Coastguard Worker }
150*f6dc9357SAndroid Build Coastguard Worker return *this;
151*f6dc9357SAndroid Build Coastguard Worker }
152*f6dc9357SAndroid Build Coastguard Worker
operator =(const char * s)153*f6dc9357SAndroid Build Coastguard Worker CPropVariant& CPropVariant::operator=(const char *s)
154*f6dc9357SAndroid Build Coastguard Worker {
155*f6dc9357SAndroid Build Coastguard Worker InternalClear();
156*f6dc9357SAndroid Build Coastguard Worker vt = VT_BSTR;
157*f6dc9357SAndroid Build Coastguard Worker wReserved1 = 0;
158*f6dc9357SAndroid Build Coastguard Worker bstrVal = AllocBstrFromAscii(s);
159*f6dc9357SAndroid Build Coastguard Worker if (!bstrVal)
160*f6dc9357SAndroid Build Coastguard Worker {
161*f6dc9357SAndroid Build Coastguard Worker throw kMemException;
162*f6dc9357SAndroid Build Coastguard Worker // vt = VT_ERROR;
163*f6dc9357SAndroid Build Coastguard Worker // scode = E_OUTOFMEMORY;
164*f6dc9357SAndroid Build Coastguard Worker }
165*f6dc9357SAndroid Build Coastguard Worker return *this;
166*f6dc9357SAndroid Build Coastguard Worker }
167*f6dc9357SAndroid Build Coastguard Worker
operator =(bool bSrc)168*f6dc9357SAndroid Build Coastguard Worker CPropVariant& CPropVariant::operator=(bool bSrc) throw()
169*f6dc9357SAndroid Build Coastguard Worker {
170*f6dc9357SAndroid Build Coastguard Worker if (vt != VT_BOOL)
171*f6dc9357SAndroid Build Coastguard Worker {
172*f6dc9357SAndroid Build Coastguard Worker InternalClear();
173*f6dc9357SAndroid Build Coastguard Worker vt = VT_BOOL;
174*f6dc9357SAndroid Build Coastguard Worker }
175*f6dc9357SAndroid Build Coastguard Worker boolVal = bSrc ? VARIANT_TRUE : VARIANT_FALSE;
176*f6dc9357SAndroid Build Coastguard Worker return *this;
177*f6dc9357SAndroid Build Coastguard Worker }
178*f6dc9357SAndroid Build Coastguard Worker
AllocBstr(unsigned numChars)179*f6dc9357SAndroid Build Coastguard Worker BSTR CPropVariant::AllocBstr(unsigned numChars)
180*f6dc9357SAndroid Build Coastguard Worker {
181*f6dc9357SAndroid Build Coastguard Worker if (vt != VT_EMPTY)
182*f6dc9357SAndroid Build Coastguard Worker InternalClear();
183*f6dc9357SAndroid Build Coastguard Worker vt = VT_BSTR;
184*f6dc9357SAndroid Build Coastguard Worker wReserved1 = 0;
185*f6dc9357SAndroid Build Coastguard Worker bstrVal = ::SysAllocStringLen(NULL, numChars);
186*f6dc9357SAndroid Build Coastguard Worker if (!bstrVal)
187*f6dc9357SAndroid Build Coastguard Worker {
188*f6dc9357SAndroid Build Coastguard Worker throw kMemException;
189*f6dc9357SAndroid Build Coastguard Worker // vt = VT_ERROR;
190*f6dc9357SAndroid Build Coastguard Worker // scode = E_OUTOFMEMORY;
191*f6dc9357SAndroid Build Coastguard Worker }
192*f6dc9357SAndroid Build Coastguard Worker return bstrVal;
193*f6dc9357SAndroid Build Coastguard Worker }
194*f6dc9357SAndroid Build Coastguard Worker
195*f6dc9357SAndroid Build Coastguard Worker #define SET_PROP_id_dest(id, dest) \
196*f6dc9357SAndroid Build Coastguard Worker if (vt != id) { InternalClear(); vt = id; } dest = value; wReserved1 = 0;
197*f6dc9357SAndroid Build Coastguard Worker
Set_Int32(Int32 value)198*f6dc9357SAndroid Build Coastguard Worker void CPropVariant::Set_Int32(Int32 value) throw()
199*f6dc9357SAndroid Build Coastguard Worker {
200*f6dc9357SAndroid Build Coastguard Worker SET_PROP_id_dest(VT_I4, lVal)
201*f6dc9357SAndroid Build Coastguard Worker }
202*f6dc9357SAndroid Build Coastguard Worker
Set_Int64(Int64 value)203*f6dc9357SAndroid Build Coastguard Worker void CPropVariant::Set_Int64(Int64 value) throw()
204*f6dc9357SAndroid Build Coastguard Worker {
205*f6dc9357SAndroid Build Coastguard Worker SET_PROP_id_dest(VT_I8, hVal.QuadPart)
206*f6dc9357SAndroid Build Coastguard Worker }
207*f6dc9357SAndroid Build Coastguard Worker
208*f6dc9357SAndroid Build Coastguard Worker #define SET_PROP_FUNC(type, id, dest) \
209*f6dc9357SAndroid Build Coastguard Worker CPropVariant& CPropVariant::operator=(type value) throw() \
210*f6dc9357SAndroid Build Coastguard Worker { SET_PROP_id_dest(id, dest) return *this; }
211*f6dc9357SAndroid Build Coastguard Worker
SET_PROP_FUNC(Byte,VT_UI1,bVal)212*f6dc9357SAndroid Build Coastguard Worker SET_PROP_FUNC(Byte, VT_UI1, bVal)
213*f6dc9357SAndroid Build Coastguard Worker // SET_PROP_FUNC(Int16, VT_I2, iVal)
214*f6dc9357SAndroid Build Coastguard Worker // SET_PROP_FUNC(Int32, VT_I4, lVal)
215*f6dc9357SAndroid Build Coastguard Worker SET_PROP_FUNC(UInt32, VT_UI4, ulVal)
216*f6dc9357SAndroid Build Coastguard Worker SET_PROP_FUNC(UInt64, VT_UI8, uhVal.QuadPart)
217*f6dc9357SAndroid Build Coastguard Worker // SET_PROP_FUNC(Int64, VT_I8, hVal.QuadPart)
218*f6dc9357SAndroid Build Coastguard Worker SET_PROP_FUNC(const FILETIME &, VT_FILETIME, filetime)
219*f6dc9357SAndroid Build Coastguard Worker
220*f6dc9357SAndroid Build Coastguard Worker #define CASE_SIMPLE_VT_VALUES \
221*f6dc9357SAndroid Build Coastguard Worker case VT_EMPTY: \
222*f6dc9357SAndroid Build Coastguard Worker case VT_BOOL: \
223*f6dc9357SAndroid Build Coastguard Worker case VT_FILETIME: \
224*f6dc9357SAndroid Build Coastguard Worker case VT_UI8: \
225*f6dc9357SAndroid Build Coastguard Worker case VT_UI4: \
226*f6dc9357SAndroid Build Coastguard Worker case VT_UI2: \
227*f6dc9357SAndroid Build Coastguard Worker case VT_UI1: \
228*f6dc9357SAndroid Build Coastguard Worker case VT_I8: \
229*f6dc9357SAndroid Build Coastguard Worker case VT_I4: \
230*f6dc9357SAndroid Build Coastguard Worker case VT_I2: \
231*f6dc9357SAndroid Build Coastguard Worker case VT_I1: \
232*f6dc9357SAndroid Build Coastguard Worker case VT_UINT: \
233*f6dc9357SAndroid Build Coastguard Worker case VT_INT: \
234*f6dc9357SAndroid Build Coastguard Worker case VT_NULL: \
235*f6dc9357SAndroid Build Coastguard Worker case VT_ERROR: \
236*f6dc9357SAndroid Build Coastguard Worker case VT_R4: \
237*f6dc9357SAndroid Build Coastguard Worker case VT_R8: \
238*f6dc9357SAndroid Build Coastguard Worker case VT_CY: \
239*f6dc9357SAndroid Build Coastguard Worker case VT_DATE: \
240*f6dc9357SAndroid Build Coastguard Worker
241*f6dc9357SAndroid Build Coastguard Worker
242*f6dc9357SAndroid Build Coastguard Worker /*
243*f6dc9357SAndroid Build Coastguard Worker ::VariantClear() and ::VariantCopy() don't work, if (vt == VT_FILETIME)
244*f6dc9357SAndroid Build Coastguard Worker So we handle VT_FILETIME and another simple types directly
245*f6dc9357SAndroid Build Coastguard Worker we call system functions for VT_BSTR and for unknown typed
246*f6dc9357SAndroid Build Coastguard Worker */
247*f6dc9357SAndroid Build Coastguard Worker
248*f6dc9357SAndroid Build Coastguard Worker CPropVariant::~CPropVariant() throw()
249*f6dc9357SAndroid Build Coastguard Worker {
250*f6dc9357SAndroid Build Coastguard Worker switch ((unsigned)vt)
251*f6dc9357SAndroid Build Coastguard Worker {
252*f6dc9357SAndroid Build Coastguard Worker CASE_SIMPLE_VT_VALUES
253*f6dc9357SAndroid Build Coastguard Worker // vt = VT_EMPTY; // it's optional
254*f6dc9357SAndroid Build Coastguard Worker return;
255*f6dc9357SAndroid Build Coastguard Worker default: break;
256*f6dc9357SAndroid Build Coastguard Worker }
257*f6dc9357SAndroid Build Coastguard Worker ::VariantClear((tagVARIANT *)this);
258*f6dc9357SAndroid Build Coastguard Worker }
259*f6dc9357SAndroid Build Coastguard Worker
PropVariant_Clear(PROPVARIANT * prop)260*f6dc9357SAndroid Build Coastguard Worker HRESULT PropVariant_Clear(PROPVARIANT *prop) throw()
261*f6dc9357SAndroid Build Coastguard Worker {
262*f6dc9357SAndroid Build Coastguard Worker switch ((unsigned)prop->vt)
263*f6dc9357SAndroid Build Coastguard Worker {
264*f6dc9357SAndroid Build Coastguard Worker CASE_SIMPLE_VT_VALUES
265*f6dc9357SAndroid Build Coastguard Worker prop->vt = VT_EMPTY;
266*f6dc9357SAndroid Build Coastguard Worker break;
267*f6dc9357SAndroid Build Coastguard Worker default:
268*f6dc9357SAndroid Build Coastguard Worker {
269*f6dc9357SAndroid Build Coastguard Worker const HRESULT res = ::VariantClear((VARIANTARG *)prop);
270*f6dc9357SAndroid Build Coastguard Worker if (res != S_OK || prop->vt != VT_EMPTY)
271*f6dc9357SAndroid Build Coastguard Worker return res;
272*f6dc9357SAndroid Build Coastguard Worker break;
273*f6dc9357SAndroid Build Coastguard Worker }
274*f6dc9357SAndroid Build Coastguard Worker }
275*f6dc9357SAndroid Build Coastguard Worker prop->wReserved1 = 0;
276*f6dc9357SAndroid Build Coastguard Worker prop->wReserved2 = 0;
277*f6dc9357SAndroid Build Coastguard Worker prop->wReserved3 = 0;
278*f6dc9357SAndroid Build Coastguard Worker prop->uhVal.QuadPart = 0;
279*f6dc9357SAndroid Build Coastguard Worker return S_OK;
280*f6dc9357SAndroid Build Coastguard Worker }
281*f6dc9357SAndroid Build Coastguard Worker
Clear()282*f6dc9357SAndroid Build Coastguard Worker HRESULT CPropVariant::Clear() throw()
283*f6dc9357SAndroid Build Coastguard Worker {
284*f6dc9357SAndroid Build Coastguard Worker if (vt == VT_EMPTY)
285*f6dc9357SAndroid Build Coastguard Worker {
286*f6dc9357SAndroid Build Coastguard Worker wReserved1 = 0;
287*f6dc9357SAndroid Build Coastguard Worker return S_OK;
288*f6dc9357SAndroid Build Coastguard Worker }
289*f6dc9357SAndroid Build Coastguard Worker return PropVariant_Clear(this);
290*f6dc9357SAndroid Build Coastguard Worker }
291*f6dc9357SAndroid Build Coastguard Worker
Copy(const PROPVARIANT * pSrc)292*f6dc9357SAndroid Build Coastguard Worker HRESULT CPropVariant::Copy(const PROPVARIANT* pSrc) throw()
293*f6dc9357SAndroid Build Coastguard Worker {
294*f6dc9357SAndroid Build Coastguard Worker Clear();
295*f6dc9357SAndroid Build Coastguard Worker switch ((unsigned)pSrc->vt)
296*f6dc9357SAndroid Build Coastguard Worker {
297*f6dc9357SAndroid Build Coastguard Worker CASE_SIMPLE_VT_VALUES
298*f6dc9357SAndroid Build Coastguard Worker memmove((PROPVARIANT*)this, pSrc, sizeof(PROPVARIANT));
299*f6dc9357SAndroid Build Coastguard Worker return S_OK;
300*f6dc9357SAndroid Build Coastguard Worker default: break;
301*f6dc9357SAndroid Build Coastguard Worker }
302*f6dc9357SAndroid Build Coastguard Worker return ::VariantCopy((tagVARIANT *)this, (tagVARIANT *)const_cast<PROPVARIANT *>(pSrc));
303*f6dc9357SAndroid Build Coastguard Worker }
304*f6dc9357SAndroid Build Coastguard Worker
305*f6dc9357SAndroid Build Coastguard Worker
Attach(PROPVARIANT * pSrc)306*f6dc9357SAndroid Build Coastguard Worker HRESULT CPropVariant::Attach(PROPVARIANT *pSrc) throw()
307*f6dc9357SAndroid Build Coastguard Worker {
308*f6dc9357SAndroid Build Coastguard Worker const HRESULT hr = Clear();
309*f6dc9357SAndroid Build Coastguard Worker if (FAILED(hr))
310*f6dc9357SAndroid Build Coastguard Worker return hr;
311*f6dc9357SAndroid Build Coastguard Worker // memcpy((PROPVARIANT *)this, pSrc, sizeof(PROPVARIANT));
312*f6dc9357SAndroid Build Coastguard Worker *(PROPVARIANT *)this = *pSrc;
313*f6dc9357SAndroid Build Coastguard Worker pSrc->vt = VT_EMPTY;
314*f6dc9357SAndroid Build Coastguard Worker pSrc->wReserved1 = 0;
315*f6dc9357SAndroid Build Coastguard Worker return S_OK;
316*f6dc9357SAndroid Build Coastguard Worker }
317*f6dc9357SAndroid Build Coastguard Worker
Detach(PROPVARIANT * pDest)318*f6dc9357SAndroid Build Coastguard Worker HRESULT CPropVariant::Detach(PROPVARIANT *pDest) throw()
319*f6dc9357SAndroid Build Coastguard Worker {
320*f6dc9357SAndroid Build Coastguard Worker if (pDest->vt != VT_EMPTY)
321*f6dc9357SAndroid Build Coastguard Worker {
322*f6dc9357SAndroid Build Coastguard Worker const HRESULT hr = PropVariant_Clear(pDest);
323*f6dc9357SAndroid Build Coastguard Worker if (FAILED(hr))
324*f6dc9357SAndroid Build Coastguard Worker return hr;
325*f6dc9357SAndroid Build Coastguard Worker }
326*f6dc9357SAndroid Build Coastguard Worker // memcpy(pDest, this, sizeof(PROPVARIANT));
327*f6dc9357SAndroid Build Coastguard Worker *pDest = *(PROPVARIANT *)this;
328*f6dc9357SAndroid Build Coastguard Worker vt = VT_EMPTY;
329*f6dc9357SAndroid Build Coastguard Worker wReserved1 = 0;
330*f6dc9357SAndroid Build Coastguard Worker return S_OK;
331*f6dc9357SAndroid Build Coastguard Worker }
332*f6dc9357SAndroid Build Coastguard Worker
InternalClear()333*f6dc9357SAndroid Build Coastguard Worker HRESULT CPropVariant::InternalClear() throw()
334*f6dc9357SAndroid Build Coastguard Worker {
335*f6dc9357SAndroid Build Coastguard Worker if (vt == VT_EMPTY)
336*f6dc9357SAndroid Build Coastguard Worker {
337*f6dc9357SAndroid Build Coastguard Worker wReserved1 = 0;
338*f6dc9357SAndroid Build Coastguard Worker return S_OK;
339*f6dc9357SAndroid Build Coastguard Worker }
340*f6dc9357SAndroid Build Coastguard Worker const HRESULT hr = Clear();
341*f6dc9357SAndroid Build Coastguard Worker if (FAILED(hr))
342*f6dc9357SAndroid Build Coastguard Worker {
343*f6dc9357SAndroid Build Coastguard Worker vt = VT_ERROR;
344*f6dc9357SAndroid Build Coastguard Worker scode = hr;
345*f6dc9357SAndroid Build Coastguard Worker }
346*f6dc9357SAndroid Build Coastguard Worker return hr;
347*f6dc9357SAndroid Build Coastguard Worker }
348*f6dc9357SAndroid Build Coastguard Worker
InternalCopy(const PROPVARIANT * pSrc)349*f6dc9357SAndroid Build Coastguard Worker void CPropVariant::InternalCopy(const PROPVARIANT *pSrc)
350*f6dc9357SAndroid Build Coastguard Worker {
351*f6dc9357SAndroid Build Coastguard Worker const HRESULT hr = Copy(pSrc);
352*f6dc9357SAndroid Build Coastguard Worker if (FAILED(hr))
353*f6dc9357SAndroid Build Coastguard Worker {
354*f6dc9357SAndroid Build Coastguard Worker if (hr == E_OUTOFMEMORY)
355*f6dc9357SAndroid Build Coastguard Worker throw kMemException;
356*f6dc9357SAndroid Build Coastguard Worker vt = VT_ERROR;
357*f6dc9357SAndroid Build Coastguard Worker scode = hr;
358*f6dc9357SAndroid Build Coastguard Worker }
359*f6dc9357SAndroid Build Coastguard Worker }
360*f6dc9357SAndroid Build Coastguard Worker
361*f6dc9357SAndroid Build Coastguard Worker
Compare(const CPropVariant & a)362*f6dc9357SAndroid Build Coastguard Worker int CPropVariant::Compare(const CPropVariant &a) throw()
363*f6dc9357SAndroid Build Coastguard Worker {
364*f6dc9357SAndroid Build Coastguard Worker if (vt != a.vt)
365*f6dc9357SAndroid Build Coastguard Worker return MyCompare(vt, a.vt);
366*f6dc9357SAndroid Build Coastguard Worker switch ((unsigned)vt)
367*f6dc9357SAndroid Build Coastguard Worker {
368*f6dc9357SAndroid Build Coastguard Worker case VT_EMPTY: return 0;
369*f6dc9357SAndroid Build Coastguard Worker // case VT_I1: return MyCompare(cVal, a.cVal);
370*f6dc9357SAndroid Build Coastguard Worker case VT_UI1: return MyCompare(bVal, a.bVal);
371*f6dc9357SAndroid Build Coastguard Worker case VT_I2: return MyCompare(iVal, a.iVal);
372*f6dc9357SAndroid Build Coastguard Worker case VT_UI2: return MyCompare(uiVal, a.uiVal);
373*f6dc9357SAndroid Build Coastguard Worker case VT_I4: return MyCompare(lVal, a.lVal);
374*f6dc9357SAndroid Build Coastguard Worker case VT_UI4: return MyCompare(ulVal, a.ulVal);
375*f6dc9357SAndroid Build Coastguard Worker // case VT_UINT: return MyCompare(uintVal, a.uintVal);
376*f6dc9357SAndroid Build Coastguard Worker case VT_I8: return MyCompare(hVal.QuadPart, a.hVal.QuadPart);
377*f6dc9357SAndroid Build Coastguard Worker case VT_UI8: return MyCompare(uhVal.QuadPart, a.uhVal.QuadPart);
378*f6dc9357SAndroid Build Coastguard Worker case VT_BOOL: return -MyCompare(boolVal, a.boolVal);
379*f6dc9357SAndroid Build Coastguard Worker case VT_FILETIME:
380*f6dc9357SAndroid Build Coastguard Worker {
381*f6dc9357SAndroid Build Coastguard Worker const int res = CompareFileTime(&filetime, &a.filetime);
382*f6dc9357SAndroid Build Coastguard Worker if (res != 0)
383*f6dc9357SAndroid Build Coastguard Worker return res;
384*f6dc9357SAndroid Build Coastguard Worker const unsigned v1 = Get_Ns100();
385*f6dc9357SAndroid Build Coastguard Worker const unsigned v2 = a.Get_Ns100();
386*f6dc9357SAndroid Build Coastguard Worker return MyCompare(v1, v2);
387*f6dc9357SAndroid Build Coastguard Worker }
388*f6dc9357SAndroid Build Coastguard Worker case VT_BSTR: return 0; // Not implemented
389*f6dc9357SAndroid Build Coastguard Worker default: return 0;
390*f6dc9357SAndroid Build Coastguard Worker }
391*f6dc9357SAndroid Build Coastguard Worker }
392*f6dc9357SAndroid Build Coastguard Worker
393*f6dc9357SAndroid Build Coastguard Worker }}
394