2 * Copyright 2019 Hans Leidekker for CodeWeavers
4 * This library is free software; you can redistribute it and/or
5 * modify it under the terms of the GNU Lesser General Public
6 * License as published by the Free Software Foundation; either
7 * version 2.1 of the License, or (at your option) any later version.
9 * This library is distributed in the hope that it will be useful,
10 * but WITHOUT ANY WARRANTY; without even the implied warranty of
11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
12 * Lesser General Public License for more details.
14 * You should have received a copy of the GNU Lesser General Public
15 * License along with this library; if not, write to the Free Software
16 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
24 #include <msado15_backcompat.h>
25 #include "wine/test.h"
28 DEFINE_GUID(DBPROPSET_ROWSET
, 0xc8b522be, 0x5cf3, 0x11ce, 0xad, 0xe5, 0x00, 0xaa, 0x00, 0x44, 0x77, 0x3d);
30 #define MAKE_ADO_HRESULT( err ) MAKE_HRESULT( SEVERITY_ERROR, FACILITY_CONTROL, err )
32 static BOOL
is_bof( _Recordset
*recordset
)
34 VARIANT_BOOL bof
= VARIANT_FALSE
;
35 _Recordset_get_BOF( recordset
, &bof
);
36 return bof
== VARIANT_TRUE
;
39 static BOOL
is_eof( _Recordset
*recordset
)
41 VARIANT_BOOL eof
= VARIANT_FALSE
;
42 _Recordset_get_EOF( recordset
, &eof
);
43 return eof
== VARIANT_TRUE
;
46 static void test_Recordset(void)
48 _Recordset
*recordset
;
49 IRunnableObject
*runtime
;
50 ISupportErrorInfo
*errorinfo
;
51 Fields
*fields
, *fields2
;
56 VARIANT missing
, val
, index
;
57 CursorLocationEnum location
;
58 CursorTypeEnum cursor
;
63 hr
= CoCreateInstance( &CLSID_Recordset
, NULL
, CLSCTX_INPROC_SERVER
, &IID__Recordset
, (void **)&recordset
);
64 ok( hr
== S_OK
, "got %08x\n", hr
);
66 hr
= _Recordset_QueryInterface( recordset
, &IID_IRunnableObject
, (void**)&runtime
);
67 ok(hr
== E_NOINTERFACE
, "Unexpected IRunnableObject interface\n");
68 ok(runtime
== NULL
, "expected NULL\n");
70 /* _Recordset object supports ISupportErrorInfo */
72 hr
= _Recordset_QueryInterface( recordset
, &IID_ISupportErrorInfo
, (void **)&errorinfo
);
73 ok( hr
== S_OK
, "got %08x\n", hr
);
74 if (errorinfo
) ISupportErrorInfo_Release( errorinfo
);
76 hr
= _Recordset_get_Fields( recordset
, &fields
);
77 ok( hr
== S_OK
, "got %08x\n", hr
);
79 /* calling get_Fields again returns the same object */
80 hr
= _Recordset_get_Fields( recordset
, &fields2
);
81 ok( hr
== S_OK
, "got %08x\n", hr
);
82 ok( fields2
== fields
, "expected same object\n" );
85 hr
= Fields_get_Count( fields2
, &count
);
86 ok( hr
== S_OK
, "got %08x\n", hr
);
87 ok( !count
, "got %d\n", count
);
89 hr
= _Recordset_Close( recordset
);
90 ok( hr
== MAKE_ADO_HRESULT( adErrObjectClosed
), "got %08x\n", hr
);
92 Fields_Release( fields2
);
94 hr
= CoCreateInstance( &CLSID_Recordset
, NULL
, CLSCTX_INPROC_SERVER
, &IID__Recordset
, (void **)&recordset
);
95 ok( hr
== S_OK
, "got %08x\n", hr
);
98 hr
= _Recordset_get_State( recordset
, &state
);
99 ok( hr
== S_OK
, "got %08x\n", hr
);
100 ok( state
== adStateClosed
, "got %d\n", state
);
103 hr
= _Recordset_get_CursorLocation( recordset
, &location
);
104 ok( hr
== S_OK
, "got %08x\n", hr
);
105 ok( location
== adUseServer
, "got %d\n", location
);
107 cursor
= adOpenUnspecified
;
108 hr
= _Recordset_get_CursorType( recordset
, &cursor
);
109 ok( hr
== S_OK
, "got %08x\n", hr
);
110 ok( cursor
== adOpenForwardOnly
, "got %d\n", cursor
);
112 VariantInit( &bookmark
);
113 hr
= _Recordset_get_Bookmark( recordset
, &bookmark
);
114 ok( hr
== MAKE_ADO_HRESULT( adErrObjectClosed
), "got %08x\n", hr
);
116 VariantInit( &bookmark
);
117 hr
= _Recordset_put_Bookmark( recordset
, bookmark
);
118 ok( hr
== MAKE_ADO_HRESULT( adErrObjectClosed
), "got %08x\n", hr
);
120 VariantInit( &missing
);
121 hr
= _Recordset_AddNew( recordset
, missing
, missing
);
122 ok( hr
== MAKE_ADO_HRESULT( adErrObjectClosed
), "got %08x\n", hr
);
124 V_VT( &missing
) = VT_ERROR
;
125 V_ERROR( &missing
) = DISP_E_PARAMNOTFOUND
;
126 hr
= _Recordset_Open( recordset
, missing
, missing
, adOpenStatic
, adLockBatchOptimistic
, adCmdUnspecified
);
127 ok( hr
== MAKE_ADO_HRESULT( adErrInvalidConnection
), "got %08x\n", hr
);
129 hr
= _Recordset_get_Fields( recordset
, &fields
);
130 ok( hr
== S_OK
, "got %08x\n", hr
);
132 name
= SysAllocString( L
"field" );
133 hr
= Fields__Append( fields
, name
, adInteger
, 4, adFldUnspecified
);
134 ok( hr
== S_OK
, "got %08x\n", hr
);
136 V_VT( &index
) = VT_I4
;
137 V_I4( &index
) = 1000;
138 hr
= Fields_get_Item( fields
, index
, &field
);
139 ok( hr
== MAKE_ADO_HRESULT(adErrItemNotFound
), "got %08x\n", hr
);
141 V_VT( &index
) = VT_I4
;
143 hr
= Fields_get_Item( fields
, index
, &field
);
144 ok( hr
== S_OK
, "got %08x\n", hr
);
145 Field_Release(field
);
147 V_VT( &index
) = VT_I2
;
149 hr
= Fields_get_Item( fields
, index
, &field
);
150 ok( hr
== S_OK
, "got %08x\n", hr
);
151 Field_Release(field
);
153 V_VT( &index
) = VT_BSTR
;
154 V_BSTR( &index
) = name
;
155 hr
= Fields_get_Item( fields
, index
, &field
);
156 ok( hr
== S_OK
, "got %08x\n", hr
);
157 SysFreeString( name
);
159 hr
= Field_QueryInterface(field
, &IID_Properties
, (void**)&props
);
160 ok( hr
== E_NOINTERFACE
, "got %08x\n", hr
);
162 hr
= Field_get_Properties(field
, &props
);
163 ok( hr
== S_OK
, "got %08x\n", hr
);
166 hr
= Properties_get_Count(props
, &count
);
167 ok( hr
== S_OK
, "got %08x\n", hr
);
168 ok( !count
, "got %d\n", count
);
170 V_VT( &index
) = VT_I4
;
171 V_I4( &index
) = 1000;
172 hr
= Properties_get_Item(props
, index
, &prop
);
173 ok( hr
== MAKE_ADO_HRESULT(adErrItemNotFound
), "got %08x\n", hr
);
175 Properties_Release(props
);
177 hr
= _Recordset_Open( recordset
, missing
, missing
, adOpenStatic
, adLockBatchOptimistic
, adCmdUnspecified
);
178 ok( hr
== S_OK
, "got %08x\n", hr
);
179 ok( is_eof( recordset
), "not eof\n" );
180 ok( is_bof( recordset
), "not bof\n" );
182 hr
= _Recordset_Open( recordset
, missing
, missing
, adOpenStatic
, adLockBatchOptimistic
, adCmdUnspecified
);
183 ok( hr
== MAKE_ADO_HRESULT( adErrObjectOpen
), "got %08x\n", hr
);
186 hr
= _Recordset_get_State( recordset
, &state
);
187 ok( hr
== S_OK
, "got %08x\n", hr
);
188 ok( state
== adStateOpen
, "got %d\n", state
);
190 VariantInit( &bookmark
);
191 hr
= _Recordset_get_Bookmark( recordset
, &bookmark
);
192 ok( hr
== MAKE_ADO_HRESULT( adErrNoCurrentRecord
), "got %08x\n", hr
);
194 VariantInit( &bookmark
);
195 hr
= _Recordset_put_Bookmark( recordset
, bookmark
);
196 ok( hr
== MAKE_ADO_HRESULT( adErrInvalidArgument
), "got %08x\n", hr
);
199 hr
= _Recordset_get_RecordCount( recordset
, &count
);
200 ok( hr
== S_OK
, "got %08x\n", hr
);
201 ok( !count
, "got %d\n", count
);
203 hr
= _Recordset_AddNew( recordset
, missing
, missing
);
204 ok( hr
== S_OK
, "got %08x\n", hr
);
205 ok( !is_eof( recordset
), "eof\n" );
206 ok( !is_bof( recordset
), "bof\n" );
209 hr
= _Recordset_get_RecordCount( recordset
, &count
);
210 ok( hr
== S_OK
, "got %08x\n", hr
);
211 ok( count
== 1, "got %d\n", count
);
213 /* get_Fields still returns the same object */
214 hr
= _Recordset_get_Fields( recordset
, &fields2
);
215 ok( hr
== S_OK
, "got %08x\n", hr
);
216 ok( fields2
== fields
, "expected same object\n" );
217 Fields_Release( fields2
);
220 hr
= Fields_get_Count( fields2
, &count
);
221 ok( count
== 1, "got %d\n", count
);
223 hr
= Field_get_Value( field
, &val
);
224 ok( hr
== S_OK
, "got %08x\n", hr
);
225 ok( V_VT( &val
) == VT_EMPTY
, "got %u\n", V_VT( &val
) );
227 V_VT( &val
) = VT_I4
;
229 hr
= Field_put_Value( field
, val
);
230 ok( hr
== S_OK
, "got %08x\n", hr
);
232 V_VT( &val
) = VT_ERROR
;
233 V_ERROR( &val
) = DISP_E_PARAMNOTFOUND
;
234 hr
= Field_get_Value( field
, &val
);
235 ok( hr
== S_OK
, "got %08x\n", hr
);
236 ok( V_VT( &val
) == VT_I4
, "got %u\n", V_VT( &val
) );
237 ok( V_I4( &val
) == -1, "got %d\n", V_I4( &val
) );
239 hr
= _Recordset_AddNew( recordset
, missing
, missing
);
240 ok( hr
== S_OK
, "got %08x\n", hr
);
242 /* field object returns different value after AddNew */
243 V_VT( &val
) = VT_ERROR
;
244 V_ERROR( &val
) = DISP_E_PARAMNOTFOUND
;
245 hr
= Field_get_Value( field
, &val
);
246 ok( hr
== S_OK
, "got %08x\n", hr
);
247 ok( V_VT( &val
) == VT_EMPTY
, "got %u\n", V_VT( &val
) );
249 ok( !is_eof( recordset
), "eof\n" );
250 ok( !is_bof( recordset
), "bof\n" );
251 hr
= _Recordset_MoveFirst( recordset
);
252 ok( hr
== S_OK
, "got %08x\n", hr
);
253 ok( !is_eof( recordset
), "eof\n" );
254 ok( !is_bof( recordset
), "bof\n" );
256 V_VT( &val
) = VT_ERROR
;
257 V_ERROR( &val
) = DISP_E_PARAMNOTFOUND
;
258 hr
= Field_get_Value( field
, &val
);
259 ok( hr
== S_OK
, "got %08x\n", hr
);
260 ok( V_VT( &val
) == VT_I4
, "got %u\n", V_VT( &val
) );
261 ok( V_I4( &val
) == -1, "got %d\n", V_I4( &val
) );
263 hr
= _Recordset_MoveNext( recordset
);
264 ok( hr
== S_OK
, "got %08x\n", hr
);
265 ok( !is_eof( recordset
), "eof\n" );
266 ok( !is_bof( recordset
), "not bof\n" );
268 hr
= _Recordset_MoveNext( recordset
);
269 ok( hr
== S_OK
, "got %08x\n", hr
);
270 ok( is_eof( recordset
), "not eof\n" );
271 ok( !is_bof( recordset
), "bof\n" );
273 hr
= _Recordset_MoveFirst( recordset
);
274 ok( hr
== S_OK
, "got %08x\n", hr
);
275 ok( !is_eof( recordset
), "eof\n" );
276 ok( !is_bof( recordset
), "bof\n" );
278 hr
= _Recordset_MovePrevious( recordset
);
279 ok( hr
== S_OK
, "got %08x\n", hr
);
280 ok( !is_eof( recordset
), "eof\n" );
281 ok( is_bof( recordset
), "not bof\n" );
283 /* try get value at BOF */
285 hr
= Field_get_Value( field
, &val
);
286 ok( hr
== MAKE_ADO_HRESULT( adErrNoCurrentRecord
), "got %08x\n", hr
);
288 hr
= _Recordset_Close( recordset
);
289 ok( hr
== S_OK
, "got %08x\n", hr
);
292 hr
= Fields_get_Count( fields
, &count
);
293 ok( !count
, "got %d\n", count
);
295 hr
= Field_get_Name(field
, &name
);
296 todo_wine
ok( hr
== MAKE_ADO_HRESULT( adErrObjectNotSet
), "got %08x\n", hr
);
299 hr
= _Recordset_get_State( recordset
, &state
);
300 ok( hr
== S_OK
, "got %08x\n", hr
);
301 ok( state
== adStateClosed
, "got %d\n", state
);
303 Field_Release( field
);
304 Fields_Release( fields
);
305 _Recordset_Release( recordset
);
308 /* This interface is queried for but is not documented anywhere. */
309 DEFINE_GUID(UKN_INTERFACE
, 0x6f1e39e1, 0x05c6, 0x11d0, 0xa7, 0x8b, 0x00, 0xaa, 0x00, 0xa3, 0xf0, 0x0d);
313 IRowset IRowset_iface
;
314 IRowsetInfo IRowsetInfo_iface
;
315 IColumnsInfo IColumnsInfo_iface
;
319 static inline struct test_rowset
*impl_from_IRowset( IRowset
*iface
)
321 return CONTAINING_RECORD( iface
, struct test_rowset
, IRowset_iface
);
324 static inline struct test_rowset
*impl_from_IRowsetInfo( IRowsetInfo
*iface
)
326 return CONTAINING_RECORD( iface
, struct test_rowset
, IRowsetInfo_iface
);
329 static inline struct test_rowset
*impl_from_IColumnsInfo( IColumnsInfo
*iface
)
331 return CONTAINING_RECORD( iface
, struct test_rowset
, IColumnsInfo_iface
);
334 static HRESULT WINAPI
rowset_info_QueryInterface(IRowsetInfo
*iface
, REFIID riid
, void **obj
)
336 struct test_rowset
*rowset
= impl_from_IRowsetInfo( iface
);
337 return IRowset_QueryInterface(&rowset
->IRowset_iface
, riid
, obj
);
340 static ULONG WINAPI
rowset_info_AddRef(IRowsetInfo
*iface
)
342 struct test_rowset
*rowset
= impl_from_IRowsetInfo( iface
);
343 return IRowset_AddRef(&rowset
->IRowset_iface
);
346 static ULONG WINAPI
rowset_info_Release(IRowsetInfo
*iface
)
348 struct test_rowset
*rowset
= impl_from_IRowsetInfo( iface
);
349 return IRowset_Release(&rowset
->IRowset_iface
);
352 static HRESULT WINAPI
rowset_info_GetProperties(IRowsetInfo
*iface
, const ULONG count
,
353 const DBPROPIDSET propertyidsets
[], ULONG
*out_count
, DBPROPSET
**propertysets1
)
355 ok( count
== 2, "got %d\n", count
);
357 ok( IsEqualIID(&DBPROPSET_ROWSET
, &propertyidsets
[0].guidPropertySet
), "got %s\n", wine_dbgstr_guid(&propertyidsets
[0].guidPropertySet
));
358 ok( propertyidsets
[0].cPropertyIDs
== 17, "got %d\n", propertyidsets
[0].cPropertyIDs
);
360 ok( IsEqualIID(&DBPROPSET_PROVIDERROWSET
, &propertyidsets
[1].guidPropertySet
), "got %s\n", wine_dbgstr_guid(&propertyidsets
[1].guidPropertySet
));
361 ok( propertyidsets
[1].cPropertyIDs
== 1, "got %d\n", propertyidsets
[1].cPropertyIDs
);
366 static HRESULT WINAPI
rowset_info_GetReferencedRowset(IRowsetInfo
*iface
, DBORDINAL ordinal
,
367 REFIID riid
, IUnknown
**unk
)
369 ok(0, "Unexpected call\n");
373 static HRESULT WINAPI
rowset_info_GetSpecification(IRowsetInfo
*iface
, REFIID riid
,
374 IUnknown
**specification
)
376 ok(0, "Unexpected call\n");
380 static const struct IRowsetInfoVtbl rowset_info
=
382 rowset_info_QueryInterface
,
385 rowset_info_GetProperties
,
386 rowset_info_GetReferencedRowset
,
387 rowset_info_GetSpecification
390 static HRESULT WINAPI
column_info_QueryInterface(IColumnsInfo
*iface
, REFIID riid
, void **obj
)
392 struct test_rowset
*rowset
= impl_from_IColumnsInfo( iface
);
393 return IRowset_QueryInterface(&rowset
->IRowset_iface
, riid
, obj
);
396 static ULONG WINAPI
column_info_AddRef(IColumnsInfo
*iface
)
398 struct test_rowset
*rowset
= impl_from_IColumnsInfo( iface
);
399 return IRowset_AddRef(&rowset
->IRowset_iface
);
402 static ULONG WINAPI
column_info_Release(IColumnsInfo
*iface
)
404 struct test_rowset
*rowset
= impl_from_IColumnsInfo( iface
);
405 return IRowset_Release(&rowset
->IRowset_iface
);
408 static HRESULT WINAPI
column_info_GetColumnInfo(IColumnsInfo
*This
, DBORDINAL
*columns
,
409 DBCOLUMNINFO
**colinfo
, OLECHAR
**stringsbuffer
)
411 DBCOLUMNINFO
*dbcolumn
;
414 *stringsbuffer
= CoTaskMemAlloc(sizeof(L
"Column1"));
415 lstrcpyW(*stringsbuffer
, L
"Column1");
417 dbcolumn
= CoTaskMemAlloc(sizeof(DBCOLUMNINFO
));
419 dbcolumn
->pwszName
= *stringsbuffer
;
420 dbcolumn
->pTypeInfo
= NULL
;
421 dbcolumn
->iOrdinal
= 1;
422 dbcolumn
->dwFlags
= DBCOLUMNFLAGS_MAYBENULL
;
423 dbcolumn
->ulColumnSize
= 5;
424 dbcolumn
->wType
= DBTYPE_I4
;
425 dbcolumn
->bPrecision
= 1;
426 dbcolumn
->bScale
= 1;
427 dbcolumn
->columnid
.eKind
= DBKIND_NAME
;
428 dbcolumn
->columnid
.uName
.pwszName
= *stringsbuffer
;
435 static HRESULT WINAPI
column_info_MapColumnIDs(IColumnsInfo
*This
, DBORDINAL column_ids
,
436 const DBID
*dbids
, DBORDINAL
*columns
)
438 ok(0, "Unexpected call\n");
442 static const struct IColumnsInfoVtbl column_info
=
444 column_info_QueryInterface
,
447 column_info_GetColumnInfo
,
448 column_info_MapColumnIDs
,
451 static HRESULT WINAPI
rowset_QueryInterface(IRowset
*iface
, REFIID riid
, void **obj
)
453 struct test_rowset
*rowset
= impl_from_IRowset( iface
);
457 if (IsEqualIID(riid
, &IID_IRowset
) ||
458 IsEqualIID(riid
, &IID_IUnknown
))
460 trace("Requested interface IID_IRowset\n");
461 *obj
= &rowset
->IRowset_iface
;
463 else if (IsEqualIID(riid
, &IID_IRowsetInfo
))
465 trace("Requested interface IID_IRowsetInfo\n");
466 *obj
= &rowset
->IRowsetInfo_iface
;
468 else if (IsEqualIID(riid
, &IID_IColumnsInfo
))
470 trace("Requested interface IID_IColumnsInfo\n");
471 *obj
= &rowset
->IColumnsInfo_iface
;
473 else if (IsEqualIID(riid
, &IID_IRowsetLocate
))
475 trace("Requested interface IID_IRowsetLocate\n");
476 return E_NOINTERFACE
;
478 else if (IsEqualIID(riid
, &IID_IDBAsynchStatus
))
480 trace("Requested interface IID_IDBAsynchStatus\n");
481 return E_NOINTERFACE
;
483 else if (IsEqualIID(riid
, &IID_IAccessor
))
485 trace("Requested interface IID_IAccessor\n");
486 return E_NOINTERFACE
;
488 else if (IsEqualIID(riid
, &UKN_INTERFACE
))
490 trace("Unknown interface\n");
491 return E_NOINTERFACE
;
495 IUnknown_AddRef((IUnknown
*)*obj
);
499 ok(0, "Unsupported interface %s\n", wine_dbgstr_guid(riid
));
500 return E_NOINTERFACE
;
503 static ULONG WINAPI
rowset_AddRef(IRowset
*iface
)
505 struct test_rowset
*rowset
= impl_from_IRowset( iface
);
506 return InterlockedIncrement( &rowset
->refs
);
509 static ULONG WINAPI
rowset_Release(IRowset
*iface
)
511 struct test_rowset
*rowset
= impl_from_IRowset( iface
);
512 /* Object not allocated no need to destroy */
513 return InterlockedDecrement( &rowset
->refs
);
516 static HRESULT WINAPI
rowset_AddRefRows(IRowset
*iface
, DBCOUNTITEM cRows
, const HROW rghRows
[],
517 DBREFCOUNT rgRefCounts
[], DBROWSTATUS rgRowStatus
[])
519 ok(0, "Unexpected call\n");
523 static HRESULT WINAPI
rowset_GetData(IRowset
*iface
, HROW hRow
, HACCESSOR hAccessor
, void *pData
)
525 ok(0, "Unexpected call\n");
529 static HRESULT WINAPI
rowset_GetNextRows(IRowset
*iface
, HCHAPTER hReserved
, DBROWOFFSET lRowsOffset
,
530 DBROWCOUNT cRows
, DBCOUNTITEM
*pcRowObtained
, HROW
**prghRows
)
532 ok(0, "Unexpected call\n");
536 static HRESULT WINAPI
rowset_ReleaseRows(IRowset
*iface
, DBCOUNTITEM cRows
, const HROW rghRows
[],
537 DBROWOPTIONS rgRowOptions
[], DBREFCOUNT rgRefCounts
[], DBROWSTATUS rgRowStatus
[])
539 ok(0, "Unexpected call\n");
543 static HRESULT WINAPI
rowset_RestartPosition(IRowset
*iface
, HCHAPTER hReserved
)
545 ok(0, "Unexpected call\n");
549 static const struct IRowsetVtbl rowset_vtbl
=
551 rowset_QueryInterface
,
558 rowset_RestartPosition
561 static ULONG
get_refcount(void *iface
)
563 IUnknown
*unknown
= iface
;
564 IUnknown_AddRef(unknown
);
565 return IUnknown_Release(unknown
);
568 static void test_ADORecordsetConstruction(void)
570 _Recordset
*recordset
;
571 ADORecordsetConstruction
*construct
;
572 Fields
*fields
= NULL
;
574 struct test_rowset testrowset
;
579 hr
= CoCreateInstance( &CLSID_Recordset
, NULL
, CLSCTX_INPROC_SERVER
, &IID__Recordset
, (void **)&recordset
);
580 ok( hr
== S_OK
, "got %08x\n", hr
);
582 hr
= _Recordset_QueryInterface( recordset
, &IID_ADORecordsetConstruction
, (void**)&construct
);
583 ok( hr
== S_OK
, "got %08x\n", hr
);
589 testrowset
.IRowset_iface
.lpVtbl
= &rowset_vtbl
;
590 testrowset
.IRowsetInfo_iface
.lpVtbl
= &rowset_info
;
591 testrowset
.IColumnsInfo_iface
.lpVtbl
= &column_info
;
594 rowset
= &testrowset
.IRowset_iface
;
596 ref
= get_refcount( rowset
);
597 ok( ref
== 1, "got %d\n", ref
);
598 hr
= ADORecordsetConstruction_put_Rowset( construct
, (IUnknown
*)rowset
);
599 ok( hr
== S_OK
, "got %08x\n", hr
);
601 ref
= get_refcount( rowset
);
602 ok( ref
== 2, "got %d\n", ref
);
604 hr
= _Recordset_get_Fields( recordset
, &fields
);
605 ok( hr
== S_OK
, "got %08x\n", hr
);
606 ok( fields
!= NULL
, "NULL value\n");
608 ref
= get_refcount( rowset
);
609 ok( ref
== 2, "got %d\n", ref
);
612 hr
= Fields_get_Count( fields
, &count
);
613 ok( count
== 1, "got %d\n", count
);
620 V_VT( &index
) = VT_BSTR
;
621 V_BSTR( &index
) = SysAllocString( L
"Column1" );
623 hr
= Fields_get_Item( fields
, index
, &field
);
624 ok( hr
== S_OK
, "got %08x\n", hr
);
626 hr
= Field_get_Type( field
, &type
);
627 ok( hr
== S_OK
, "got %08x\n", hr
);
628 ok( type
== adInteger
, "got %d\n", type
);
630 hr
= Field_get_DefinedSize( field
, &size
);
631 ok( hr
== S_OK
, "got %08x\n", hr
);
632 ok( size
== 5, "got %d\n", size
);
634 VariantClear(&index
);
636 Field_Release(field
);
639 ref
= get_refcount(rowset
);
640 ok( ref
== 2, "got %d\n", ref
);
642 Fields_Release(fields
);
644 ADORecordsetConstruction_Release(construct
);
647 _Recordset_Release( recordset
);
650 static void test_Fields(void)
652 _Recordset
*recordset
;
653 ISupportErrorInfo
*errorinfo
;
655 Field
*field
, *field2
;
660 FieldAttributeEnum attrs
;
663 hr
= CoCreateInstance( &CLSID_Recordset
, NULL
, CLSCTX_INPROC_SERVER
, &IID__Recordset
, (void **)&recordset
);
664 ok( hr
== S_OK
, "got %08x\n", hr
);
666 hr
= _Recordset_QueryInterface( recordset
, &IID_Fields
, (void **)&fields
);
667 ok( hr
== E_NOINTERFACE
, "got %08x\n", hr
);
669 hr
= _Recordset_get_Fields( recordset
, &fields
);
670 ok( hr
== S_OK
, "got %08x\n", hr
);
672 /* Fields object supports ISupportErrorInfo */
674 hr
= Fields_QueryInterface( fields
, &IID_ISupportErrorInfo
, (void **)&errorinfo
);
675 ok( hr
== S_OK
, "got %08x\n", hr
);
676 if (errorinfo
) ISupportErrorInfo_Release( errorinfo
);
679 hr
= Fields_get_Count( fields
, &count
);
680 ok( !count
, "got %d\n", count
);
682 name
= SysAllocString( L
"field" );
683 V_VT( &val
) = VT_ERROR
;
684 V_ERROR( &val
) = DISP_E_PARAMNOTFOUND
;
685 hr
= Fields_Append( fields
, name
, adInteger
, 4, adFldUnspecified
, val
);
686 ok( hr
== S_OK
, "got %08x\n", hr
);
687 SysFreeString( name
);
690 hr
= Fields_get_Count( fields
, &count
);
691 ok( count
== 1, "got %d\n", count
);
693 name
= SysAllocString( L
"field2" );
694 hr
= Fields__Append( fields
, name
, adInteger
, 4, adFldUnspecified
);
695 ok( hr
== S_OK
, "got %08x\n", hr
);
696 SysFreeString( name
);
699 hr
= Fields_get_Count( fields
, &count
);
700 ok( count
== 2, "got %d\n", count
);
702 /* handing out field object doesn't add reference to fields or recordset object */
703 name
= SysAllocString( L
"field" );
704 V_VT( &index
) = VT_BSTR
;
705 V_BSTR( &index
) = name
;
706 hr
= Fields_get_Item( fields
, index
, &field
);
708 /* calling get_Item again returns the same object and adds reference */
709 hr
= Fields_get_Item( fields
, index
, &field2
);
710 ok( hr
== S_OK
, "got %08x\n", hr
);
711 ok( field2
== field
, "expected same object\n" );
712 Field_Release( field2
);
713 SysFreeString( name
);
715 /* Field object supports ISupportErrorInfo */
717 hr
= Field_QueryInterface( field
, &IID_ISupportErrorInfo
, (void **)&errorinfo
);
718 ok( hr
== S_OK
, "got %08x\n", hr
);
719 if (errorinfo
) ISupportErrorInfo_Release( errorinfo
);
721 /* verify values set with _Append */
722 hr
= Field_get_Name( field
, &name
);
723 ok( hr
== S_OK
, "got %08x\n", hr
);
724 ok( !lstrcmpW( name
, L
"field" ), "got %s\n", wine_dbgstr_w(name
) );
725 SysFreeString( name
);
727 hr
= Field_get_Type( field
, &type
);
728 ok( hr
== S_OK
, "got %08x\n", hr
);
729 ok( type
== adInteger
, "got %d\n", type
);
731 hr
= Field_get_DefinedSize( field
, &size
);
732 ok( hr
== S_OK
, "got %08x\n", hr
);
733 ok( size
== 4, "got %d\n", size
);
735 hr
= Field_get_Attributes( field
, &attrs
);
736 ok( hr
== S_OK
, "got %08x\n", hr
);
737 ok( !attrs
, "got %d\n", attrs
);
739 Field_Release( field
);
740 Fields_Release( fields
);
741 _Recordset_Release( recordset
);
744 static HRESULT
str_to_byte_array( const char *data
, VARIANT
*ret
)
747 LONG i
, len
= strlen(data
);
750 if (!(vector
= SafeArrayCreateVector( VT_UI1
, 0, len
))) return E_OUTOFMEMORY
;
751 for (i
= 0; i
< len
; i
++)
753 if ((hr
= SafeArrayPutElement( vector
, &i
, (void *)&data
[i
] )) != S_OK
)
755 SafeArrayDestroy( vector
);
760 V_VT( ret
) = VT_ARRAY
| VT_UI1
;
761 V_ARRAY( ret
) = vector
;
765 static void test_Stream(void)
770 LineSeparatorEnum sep
;
771 LONG refs
, size
, pos
;
772 ObjectStateEnum state
;
773 ConnectModeEnum mode
;
775 VARIANT missing
, val
;
778 hr
= CoCreateInstance( &CLSID_Stream
, NULL
, CLSCTX_INPROC_SERVER
, &IID__Stream
, (void **)&stream
);
779 ok( hr
== S_OK
, "got %08x\n", hr
);
781 hr
= _Stream_get_Size( stream
, &size
);
782 ok( hr
== MAKE_ADO_HRESULT( adErrObjectClosed
), "got %08x\n", hr
);
784 hr
= _Stream_get_EOS( stream
, &eos
);
785 ok( hr
== MAKE_ADO_HRESULT( adErrObjectClosed
), "got %08x\n", hr
);
787 hr
= _Stream_get_Position( stream
, &pos
);
788 ok( hr
== MAKE_ADO_HRESULT( adErrObjectClosed
), "got %08x\n", hr
);
790 hr
= _Stream_put_Position( stream
, 0 );
791 ok( hr
== MAKE_ADO_HRESULT( adErrObjectClosed
), "got %08x\n", hr
);
793 /* check default type */
795 hr
= _Stream_get_Type( stream
, &type
);
796 ok( hr
== S_OK
, "got %08x\n", hr
);
797 ok( type
== adTypeText
, "got %u\n", type
);
799 hr
= _Stream_put_Type( stream
, adTypeBinary
);
800 ok( hr
== S_OK
, "got %08x\n", hr
);
803 hr
= _Stream_get_Type( stream
, &type
);
804 ok( hr
== S_OK
, "got %08x\n", hr
);
805 ok( type
== adTypeBinary
, "got %u\n", type
);
808 hr
= _Stream_put_Type( stream
, adTypeText
);
809 ok( hr
== S_OK
, "got %08x\n", hr
);
812 hr
= _Stream_get_LineSeparator( stream
, &sep
);
813 ok( hr
== S_OK
, "got %08x\n", hr
);
814 ok( sep
== adCRLF
, "got %d\n", sep
);
816 hr
= _Stream_put_LineSeparator( stream
, adLF
);
817 ok( hr
== S_OK
, "got %08x\n", hr
);
820 hr
= _Stream_get_State( stream
, &state
);
821 ok( hr
== S_OK
, "got %08x\n", hr
);
822 ok( state
== adStateClosed
, "got %u\n", state
);
825 hr
= _Stream_get_Mode( stream
, &mode
);
826 ok( hr
== S_OK
, "got %08x\n", hr
);
827 ok( mode
== adModeUnknown
, "got %u\n", mode
);
829 hr
= _Stream_put_Mode( stream
, adModeReadWrite
);
830 ok( hr
== S_OK
, "got %08x\n", hr
);
832 hr
= _Stream_get_Charset( stream
, &charset
);
833 ok( hr
== S_OK
, "got %08x\n", hr
);
834 ok( !lstrcmpW( charset
, L
"Unicode" ), "got %s\n", wine_dbgstr_w(charset
) );
835 SysFreeString( charset
);
837 str
= SysAllocString( L
"Unicode" );
838 hr
= _Stream_put_Charset( stream
, str
);
839 ok( hr
== S_OK
, "got %08x\n", hr
);
840 SysFreeString( str
);
842 hr
= _Stream_Read( stream
, 2, &val
);
843 ok( hr
== MAKE_ADO_HRESULT( adErrObjectClosed
), "got %08x\n", hr
);
845 V_VT( &missing
) = VT_ERROR
;
846 V_ERROR( &missing
) = DISP_E_PARAMNOTFOUND
;
847 hr
= _Stream_Open( stream
, missing
, adModeUnknown
, adOpenStreamUnspecified
, NULL
, NULL
);
848 ok( hr
== S_OK
, "got %08x\n", hr
);
850 hr
= _Stream_Open( stream
, missing
, adModeUnknown
, adOpenStreamUnspecified
, NULL
, NULL
);
851 ok( hr
== MAKE_ADO_HRESULT( adErrObjectOpen
), "got %08x\n", hr
);
854 hr
= _Stream_get_State( stream
, &state
);
855 ok( hr
== S_OK
, "got %08x\n", hr
);
856 ok( state
== adStateOpen
, "got %u\n", state
);
859 hr
= _Stream_get_Size( stream
, &size
);
860 ok( hr
== S_OK
, "got %08x\n", hr
);
861 ok( !size
, "got %d\n", size
);
864 hr
= _Stream_get_EOS( stream
, &eos
);
865 ok( hr
== S_OK
, "got %08x\n", hr
);
866 ok( eos
== VARIANT_TRUE
, "got %04x\n", eos
);
869 hr
= _Stream_get_Position( stream
, &pos
);
870 ok( hr
== S_OK
, "got %08x\n", hr
);
871 ok( !pos
, "got %d\n", pos
);
874 hr
= _Stream_get_Size( stream
, &size
);
875 ok( hr
== S_OK
, "got %08x\n", hr
);
876 ok( !size
, "got %d\n", size
);
878 hr
= _Stream_Read( stream
, 2, &val
);
879 ok( hr
== MAKE_ADO_HRESULT( adErrIllegalOperation
), "got %08x\n", hr
);
881 hr
= _Stream_ReadText( stream
, 2, &str
);
882 ok( hr
== S_OK
, "got %08x\n", hr
);
883 ok( !str
[0], "got %s\n", wine_dbgstr_w(str
) );
884 SysFreeString( str
);
887 hr
= _Stream_get_Position( stream
, &pos
);
888 ok( hr
== S_OK
, "got %08x\n", hr
);
889 ok( !pos
, "got %d\n", pos
);
891 str
= SysAllocString( L
"test" );
892 hr
= _Stream_WriteText( stream
, str
, adWriteChar
);
893 ok( hr
== S_OK
, "got %08x\n", hr
);
894 SysFreeString( str
);
896 hr
= _Stream_ReadText( stream
, adReadAll
, &str
);
897 ok( hr
== S_OK
, "got %08x\n", hr
);
898 ok( !str
[0], "got %s\n", wine_dbgstr_w(str
) );
899 SysFreeString( str
);
901 hr
= _Stream_put_Position( stream
, 0 );
902 ok( hr
== S_OK
, "got %08x\n", hr
);
903 hr
= _Stream_ReadText( stream
, adReadAll
, &str
);
904 ok( hr
== S_OK
, "got %08x\n", hr
);
905 ok( !lstrcmpW( str
, L
"test" ), "got %s\n", wine_dbgstr_w(str
) );
906 SysFreeString( str
);
909 hr
= _Stream_get_Position( stream
, &pos
);
910 ok( hr
== S_OK
, "got %08x\n", hr
);
911 ok( pos
== 10, "got %d\n", pos
);
914 hr
= _Stream_get_EOS( stream
, &eos
);
915 ok( hr
== S_OK
, "got %08x\n", hr
);
916 ok( eos
== VARIANT_TRUE
, "got %04x\n", eos
);
918 hr
= _Stream_put_Position( stream
, 6 );
919 ok( hr
== S_OK
, "got %08x\n", hr
);
922 hr
= _Stream_get_Size( stream
, &size
);
923 ok( hr
== S_OK
, "got %08x\n", hr
);
924 ok( size
== 10, "got %d\n", size
);
926 hr
= _Stream_put_Position( stream
, 2 );
927 ok( hr
== S_OK
, "got %08x\n", hr
);
929 hr
= _Stream_SetEOS( stream
);
930 ok( hr
== S_OK
, "got %08x\n", hr
);
933 hr
= _Stream_get_Position( stream
, &pos
);
934 ok( hr
== S_OK
, "got %08x\n", hr
);
935 ok( pos
== 2, "got %d\n", pos
);
938 hr
= _Stream_get_Size( stream
, &size
);
939 ok( hr
== S_OK
, "got %08x\n", hr
);
940 ok( size
== 2, "got %d\n", size
);
942 hr
= _Stream_Close( stream
);
943 ok( hr
== S_OK
, "got %08x\n", hr
);
946 hr
= _Stream_get_State( stream
, &state
);
947 ok( hr
== S_OK
, "got %08x\n", hr
);
948 ok( state
== adStateClosed
, "got %u\n", state
);
950 hr
= _Stream_Close( stream
);
951 ok( hr
== MAKE_ADO_HRESULT( adErrObjectClosed
), "got %08x\n", hr
);
953 refs
= _Stream_Release( stream
);
954 ok( !refs
, "got %d\n", refs
);
957 hr
= CoCreateInstance( &CLSID_Stream
, NULL
, CLSCTX_INPROC_SERVER
, &IID__Stream
, (void **)&stream
);
958 ok( hr
== S_OK
, "got %08x\n", hr
);
960 hr
= _Stream_put_Type( stream
, adTypeBinary
);
961 ok( hr
== S_OK
, "got %08x\n", hr
);
963 hr
= _Stream_Open( stream
, missing
, adModeUnknown
, adOpenStreamUnspecified
, NULL
, NULL
);
964 ok( hr
== S_OK
, "got %08x\n", hr
);
966 hr
= _Stream_ReadText( stream
, adReadAll
, &str
);
967 ok( hr
== MAKE_ADO_HRESULT( adErrIllegalOperation
), "got %08x\n", hr
);
969 str
= SysAllocString( L
"test" );
970 hr
= _Stream_WriteText( stream
, str
, adWriteChar
);
971 ok( hr
== MAKE_ADO_HRESULT( adErrIllegalOperation
), "got %08x\n", hr
);
972 SysFreeString( str
);
975 hr
= _Stream_Read( stream
, 1, &val
);
976 ok( hr
== S_OK
, "got %08x\n", hr
);
977 ok( V_VT( &val
) == VT_NULL
, "got %u\n", V_VT( &val
) );
980 hr
= _Stream_Write( stream
, val
);
981 ok( hr
== MAKE_ADO_HRESULT( adErrInvalidArgument
), "got %08x\n", hr
);
983 hr
= str_to_byte_array( "data", &val
);
984 ok( hr
== S_OK
, "got %08x\n", hr
);
985 hr
= _Stream_Write( stream
, val
);
986 ok( hr
== S_OK
, "got %08x\n", hr
);
987 VariantClear( &val
);
990 hr
= _Stream_get_Position( stream
, &pos
);
991 ok( hr
== S_OK
, "got %08x\n", hr
);
992 ok( pos
== 4, "got %d\n", pos
);
994 hr
= _Stream_put_Position( stream
, 0 );
995 ok( hr
== S_OK
, "got %08x\n", hr
);
998 hr
= _Stream_Read( stream
, adReadAll
, &val
);
999 ok( hr
== S_OK
, "got %08x\n", hr
);
1000 ok( V_VT( &val
) == (VT_ARRAY
| VT_UI1
), "got %04x\n", V_VT( &val
) );
1001 VariantClear( &val
);
1004 hr
= _Stream_get_Position( stream
, &pos
);
1005 ok( hr
== S_OK
, "got %08x\n", hr
);
1006 ok( pos
== 4, "got %d\n", pos
);
1008 refs
= _Stream_Release( stream
);
1009 ok( !refs
, "got %d\n", refs
);
1012 static void test_Connection(void)
1015 _Connection
*connection
;
1016 IRunnableObject
*runtime
;
1017 ISupportErrorInfo
*errorinfo
;
1018 IConnectionPointContainer
*pointcontainer
;
1019 ADOConnectionConstruction15
*construct
;
1020 LONG state
, timeout
;
1021 BSTR str
, str2
, str3
;
1022 ConnectModeEnum mode
;
1023 CursorLocationEnum location
;
1025 hr
= CoCreateInstance(&CLSID_Connection
, NULL
, CLSCTX_INPROC_SERVER
, &IID__Connection
, (void**)&connection
);
1026 ok( hr
== S_OK
, "got %08x\n", hr
);
1028 hr
= _Connection_QueryInterface(connection
, &IID_IRunnableObject
, (void**)&runtime
);
1029 ok(hr
== E_NOINTERFACE
, "Unexpected IRunnableObject interface\n");
1030 ok(runtime
== NULL
, "expected NULL\n");
1032 hr
= _Connection_QueryInterface(connection
, &IID_ISupportErrorInfo
, (void**)&errorinfo
);
1033 ok(hr
== S_OK
, "Failed to get ISupportErrorInfo interface\n");
1034 ISupportErrorInfo_Release(errorinfo
);
1036 hr
= _Connection_QueryInterface(connection
, &IID_IConnectionPointContainer
, (void**)&pointcontainer
);
1037 ok(hr
== S_OK
, "Failed to get IConnectionPointContainer interface %08x\n", hr
);
1038 IConnectionPointContainer_Release(pointcontainer
);
1040 hr
= _Connection_QueryInterface(connection
, &IID_ADOConnectionConstruction15
, (void**)&construct
);
1041 ok(hr
== S_OK
, "Failed to get ADOConnectionConstruction15 interface %08x\n", hr
);
1043 ADOConnectionConstruction15_Release(construct
);
1045 if (0) /* Crashes on windows */
1047 hr
= _Connection_get_State(connection
, NULL
);
1048 ok(hr
== E_INVALIDARG
, "Unexpected hr 0x%08x\n", hr
);
1052 hr
= _Connection_get_State(connection
, &state
);
1053 ok(hr
== S_OK
, "Failed to get state, hr 0x%08x\n", hr
);
1054 ok(state
== adStateClosed
, "Unexpected state value 0x%08x\n", state
);
1056 hr
= _Connection_Close(connection
);
1057 ok(hr
== MAKE_ADO_HRESULT(adErrObjectClosed
), "got %08x\n", hr
);
1060 hr
= _Connection_get_CommandTimeout(connection
, &timeout
);
1061 ok(hr
== S_OK
, "Failed to get state, hr 0x%08x\n", hr
);
1062 ok(timeout
== 30, "Unexpected timeout value %d\n", timeout
);
1064 hr
= _Connection_put_CommandTimeout(connection
, 300);
1065 ok(hr
== S_OK
, "Failed to get state, hr 0x%08x\n", hr
);
1068 hr
= _Connection_get_CommandTimeout(connection
, &timeout
);
1069 ok(hr
== S_OK
, "Failed to get state, hr 0x%08x\n", hr
);
1070 ok(timeout
== 300, "Unexpected timeout value %d\n", timeout
);
1073 hr
= _Connection_get_CursorLocation(connection
, &location
);
1074 ok(hr
== S_OK
, "Failed, hr 0x%08x\n", hr
);
1075 ok(location
== adUseServer
, "Unexpected location value %d\n", location
);
1077 hr
= _Connection_put_CursorLocation(connection
, adUseClient
);
1078 ok(hr
== S_OK
, "Failed, hr 0x%08x\n", hr
);
1081 hr
= _Connection_get_CursorLocation(connection
, &location
);
1082 ok(hr
== S_OK
, "Failed, hr 0x%08x\n", hr
);
1083 ok(location
== adUseClient
, "Unexpected location value %d\n", location
);
1085 hr
= _Connection_put_CursorLocation(connection
, adUseServer
);
1086 ok(hr
== S_OK
, "Failed, hr 0x%08x\n", hr
);
1089 hr
= _Connection_get_Mode(connection
, &mode
);
1090 ok(hr
== S_OK
, "Failed to get state, hr 0x%08x\n", hr
);
1091 ok(mode
== adModeUnknown
, "Unexpected mode value %d\n", mode
);
1093 hr
= _Connection_put_Mode(connection
, adModeShareDenyNone
);
1094 ok(hr
== S_OK
, "Failed to get state, hr 0x%08x\n", hr
);
1096 mode
= adModeUnknown
;
1097 hr
= _Connection_get_Mode(connection
, &mode
);
1098 ok(hr
== S_OK
, "Failed to get state, hr 0x%08x\n", hr
);
1099 ok(mode
== adModeShareDenyNone
, "Unexpected mode value %d\n", mode
);
1101 hr
= _Connection_put_Mode(connection
, adModeUnknown
);
1102 ok(hr
== S_OK
, "Failed to get state, hr 0x%08x\n", hr
);
1105 str
= (BSTR
)0xdeadbeef;
1106 hr
= _Connection_get_Provider(connection
, &str
);
1107 ok(hr
== S_OK
, "Failed, hr 0x%08x\n", hr
);
1108 ok(!wcscmp(str
, L
"MSDASQL"), "wrong string %s\n", wine_dbgstr_w(str
));
1111 str
= SysAllocString(L
"MSDASQL.1");
1112 hr
= _Connection_put_Provider(connection
, str
);
1113 ok(hr
== S_OK
, "Failed, hr 0x%08x\n", hr
);
1116 str
= (BSTR
)0xdeadbeef;
1117 hr
= _Connection_get_Provider(connection
, &str
);
1118 ok(hr
== S_OK
, "Failed, hr 0x%08x\n", hr
);
1119 ok(!wcscmp(str
, L
"MSDASQL.1"), "wrong string %s\n", wine_dbgstr_w(str
));
1121 /* Restore default */
1122 str
= SysAllocString(L
"MSDASQL");
1123 hr
= _Connection_put_Provider(connection
, str
);
1124 ok(hr
== S_OK
, "Failed, hr 0x%08x\n", hr
);
1127 hr
= _Connection_put_Provider(connection
, NULL
);
1128 ok(hr
== MAKE_ADO_HRESULT(adErrInvalidArgument
), "got 0x%08x\n", hr
);
1131 str
= (BSTR
)0xdeadbeef;
1132 hr
= _Connection_get_ConnectionString(connection
, &str
);
1133 ok(hr
== S_OK
, "got 0x%08x\n", hr
);
1134 ok(str
== NULL
, "got %p\n", str
);
1136 str
= SysAllocString(L
"Provider=MSDASQL.1;Persist Security Info=False;Data Source=wine_test");
1137 hr
= _Connection_put_ConnectionString(connection
, str
);
1138 ok(hr
== S_OK
, "Failed, hr 0x%08x\n", hr
);
1140 /* Show put_ConnectionString effects Provider */
1141 str3
= (BSTR
)0xdeadbeef;
1142 hr
= _Connection_get_Provider(connection
, &str3
);
1143 ok(hr
== S_OK
, "Failed, hr 0x%08x\n", hr
);
1144 ok(str3
!= NULL
, "Expected value got NULL\n");
1145 todo_wine
ok(!wcscmp(str3
, L
"MSDASQL.1"), "wrong string %s\n", wine_dbgstr_w(str3
));
1146 SysFreeString(str3
);
1148 if (0) /* Crashes on windows */
1150 hr
= _Connection_get_ConnectionString(connection
, NULL
);
1151 ok(hr
== E_POINTER
, "Failed, hr 0x%08x\n", hr
);
1155 hr
= _Connection_get_ConnectionString(connection
, &str2
);
1156 ok(hr
== S_OK
, "Failed, hr 0x%08x\n", hr
);
1157 ok(!wcscmp(str
, str2
), "wrong string %s\n", wine_dbgstr_w(str2
));
1159 hr
= _Connection_Open(connection
, NULL
, NULL
, NULL
, 0);
1160 ok(hr
== E_FAIL
, "Failed, hr 0x%08x\n", hr
);
1162 /* Open adds trailing ; if it's missing */
1163 str3
= SysAllocString(L
"Provider=MSDASQL.1;Persist Security Info=False;Data Source=wine_test;");
1164 hr
= _Connection_Open(connection
, NULL
, NULL
, NULL
, adConnectUnspecified
);
1165 ok(hr
== E_FAIL
, "Failed, hr 0x%08x\n", hr
);
1168 hr
= _Connection_get_ConnectionString(connection
, &str2
);
1169 ok(hr
== S_OK
, "Failed, hr 0x%08x\n", hr
);
1170 todo_wine
ok(!wcscmp(str3
, str2
) || broken(!wcscmp(str
, str2
)) /* XP */, "wrong string %s\n", wine_dbgstr_w(str2
));
1172 hr
= _Connection_Open(connection
, str
, NULL
, NULL
, adConnectUnspecified
);
1173 todo_wine
ok(hr
== E_FAIL
, "Failed, hr 0x%08x\n", hr
);
1177 hr
= _Connection_get_ConnectionString(connection
, &str2
);
1178 ok(hr
== S_OK
, "Failed, hr 0x%08x\n", hr
);
1179 todo_wine
ok(!wcscmp(str3
, str2
) || broken(!wcscmp(str
, str2
)) /* XP */, "wrong string %s\n", wine_dbgstr_w(str2
));
1180 SysFreeString(str2
);
1181 SysFreeString(str3
);
1183 hr
= _Connection_put_ConnectionString(connection
, NULL
);
1184 ok(hr
== S_OK
, "Failed, hr 0x%08x\n", hr
);
1186 str
= (BSTR
)0xdeadbeef;
1187 hr
= _Connection_get_ConnectionString(connection
, &str
);
1188 ok(hr
== S_OK
, "Failed, hr 0x%08x\n", hr
);
1189 ok(str
== NULL
, "got %p\n", str
);
1190 _Connection_Release(connection
);
1193 static void test_Command(void)
1198 Command15
*command15
;
1199 Command25
*command25
;
1200 CommandTypeEnum cmd_type
= adCmdUnspecified
;
1201 BSTR cmd_text
= (BSTR
)"test";
1202 _Connection
*connection
;
1204 hr
= CoCreateInstance( &CLSID_Command
, NULL
, CLSCTX_INPROC_SERVER
, &IID__Command
, (void **)&command
);
1205 ok( hr
== S_OK
, "got %08x\n", hr
);
1207 hr
= _Command_QueryInterface( command
, &IID__ADO
, (void **)&ado
);
1208 ok( hr
== S_OK
, "got %08x\n", hr
);
1209 _ADO_Release( ado
);
1211 hr
= _Command_QueryInterface( command
, &IID_Command15
, (void **)&command15
);
1212 ok( hr
== S_OK
, "got %08x\n", hr
);
1213 Command15_Release( command15
);
1215 hr
= _Command_QueryInterface( command
, &IID_Command25
, (void **)&command25
);
1216 ok( hr
== S_OK
, "got %08x\n", hr
);
1217 Command25_Release( command25
);
1219 hr
= _Command_get_CommandType( command
, &cmd_type
);
1220 ok( hr
== S_OK
, "got %08x\n", hr
);
1221 ok( cmd_type
== adCmdUnknown
, "got %08x\n", cmd_type
);
1223 _Command_put_CommandType( command
, adCmdText
);
1224 hr
= _Command_get_CommandType( command
, &cmd_type
);
1225 ok( hr
== S_OK
, "got %08x\n", hr
);
1226 ok( cmd_type
== adCmdText
, "got %08x\n", cmd_type
);
1228 hr
= _Command_put_CommandType( command
, 0xdeadbeef );
1229 ok( hr
== MAKE_ADO_HRESULT( adErrInvalidArgument
), "got %08x\n", hr
);
1231 hr
= _Command_get_CommandText( command
, &cmd_text
);
1232 ok( hr
== S_OK
, "got %08x\n", hr
);
1233 ok( !cmd_text
, "got %s\n", wine_dbgstr_w( cmd_text
));
1235 hr
= _Command_put_CommandText( command
, NULL
);
1236 ok( hr
== S_OK
, "got %08x\n", hr
);
1238 cmd_text
= SysAllocString( L
"" );
1239 hr
= _Command_put_CommandText( command
, cmd_text
);
1240 ok( hr
== S_OK
, "got %08x\n", hr
);
1241 SysFreeString( cmd_text
);
1243 hr
= _Command_get_CommandText( command
, &cmd_text
);
1244 ok( hr
== S_OK
, "got %08x\n", hr
);
1245 ok( cmd_text
&& !*cmd_text
, "got %p\n", cmd_text
);
1247 cmd_text
= SysAllocString( L
"test" );
1248 hr
= _Command_put_CommandText( command
, cmd_text
);
1249 ok( hr
== S_OK
, "got %08x\n", hr
);
1250 SysFreeString( cmd_text
);
1252 hr
= _Command_get_CommandText( command
, &cmd_text
);
1253 ok( hr
== S_OK
, "got %08x\n", hr
);
1254 ok( !wcscmp( L
"test", cmd_text
), "got %p\n", wine_dbgstr_w( cmd_text
) );
1256 connection
= (_Connection
*)0xdeadbeef;
1257 hr
= _Command_get_ActiveConnection( command
, &connection
);
1258 ok( hr
== S_OK
, "got %08x\n", hr
);
1259 ok( connection
== NULL
, "got %p\n", connection
);
1261 hr
= _Command_putref_ActiveConnection( command
, NULL
);
1262 ok( hr
== S_OK
, "got %08x\n", hr
);
1264 _Command_Release( command
);
1268 ConnectionEventsVt conn_event_sink
;
1272 static HRESULT WINAPI
conneventvt_QueryInterface( ConnectionEventsVt
*iface
, REFIID riid
, void **obj
)
1274 struct conn_event
*conn_event
= CONTAINING_RECORD( iface
, struct conn_event
, conn_event_sink
);
1276 if (IsEqualGUID( &IID_ConnectionEventsVt
, riid
))
1278 InterlockedIncrement( &conn_event
->refs
);
1283 ok( 0, "unexpected call\n" );
1284 return E_NOINTERFACE
;
1287 static ULONG WINAPI
conneventvt_AddRef( ConnectionEventsVt
*iface
)
1289 struct conn_event
*conn_event
= CONTAINING_RECORD( iface
, struct conn_event
, conn_event_sink
);
1290 return InterlockedIncrement( &conn_event
->refs
);
1293 static ULONG WINAPI
conneventvt_Release( ConnectionEventsVt
*iface
)
1295 struct conn_event
*conn_event
= CONTAINING_RECORD( iface
, struct conn_event
, conn_event_sink
);
1296 return InterlockedDecrement( &conn_event
->refs
);
1299 static HRESULT WINAPI
conneventvt_InfoMessage( ConnectionEventsVt
*iface
, Error
*error
,
1300 EventStatusEnum
*status
, _Connection
*Connection
)
1305 static HRESULT WINAPI
conneventvt_BeginTransComplete( ConnectionEventsVt
*iface
, LONG TransactionLevel
,
1306 Error
*error
, EventStatusEnum
*status
, _Connection
*connection
)
1311 static HRESULT WINAPI
conneventvt_CommitTransComplete( ConnectionEventsVt
*iface
, Error
*error
,
1312 EventStatusEnum
*status
, _Connection
*connection
)
1317 static HRESULT WINAPI
conneventvt_RollbackTransComplete( ConnectionEventsVt
*iface
, Error
*error
,
1318 EventStatusEnum
*status
, _Connection
*connection
)
1323 static HRESULT WINAPI
conneventvt_WillExecute( ConnectionEventsVt
*iface
, BSTR
*source
,
1324 CursorTypeEnum
*cursor_type
, LockTypeEnum
*lock_type
, LONG
*options
, EventStatusEnum
*status
,
1325 _Command
*command
, _Recordset
*record_set
, _Connection
*connection
)
1330 static HRESULT WINAPI
conneventvt_ExecuteComplete( ConnectionEventsVt
*iface
, LONG records_affected
,
1331 Error
*error
, EventStatusEnum
*status
, _Command
*command
, _Recordset
*record_set
,
1332 _Connection
*connection
)
1337 static HRESULT WINAPI
conneventvt_WillConnect( ConnectionEventsVt
*iface
, BSTR
*string
, BSTR
*userid
,
1338 BSTR
*password
, LONG
*options
, EventStatusEnum
*status
, _Connection
*connection
)
1343 static HRESULT WINAPI
conneventvt_ConnectComplete( ConnectionEventsVt
*iface
, Error
*error
,
1344 EventStatusEnum
*status
, _Connection
*connection
)
1349 static HRESULT WINAPI
conneventvt_Disconnect( ConnectionEventsVt
*iface
, EventStatusEnum
*status
,
1350 _Connection
*connection
)
1355 static const ConnectionEventsVtVtbl conneventvt_vtbl
= {
1356 conneventvt_QueryInterface
,
1358 conneventvt_Release
,
1359 conneventvt_InfoMessage
,
1360 conneventvt_BeginTransComplete
,
1361 conneventvt_CommitTransComplete
,
1362 conneventvt_RollbackTransComplete
,
1363 conneventvt_WillExecute
,
1364 conneventvt_ExecuteComplete
,
1365 conneventvt_WillConnect
,
1366 conneventvt_ConnectComplete
,
1367 conneventvt_Disconnect
1370 static HRESULT WINAPI
supporterror_QueryInterface( ISupportErrorInfo
*iface
, REFIID riid
, void **obj
)
1372 if (IsEqualGUID( &IID_ISupportErrorInfo
, riid
))
1378 return E_NOINTERFACE
;
1381 static ULONG WINAPI
supporterror_AddRef( ISupportErrorInfo
*iface
)
1386 static ULONG WINAPI
supporterror_Release( ISupportErrorInfo
*iface
)
1391 static HRESULT WINAPI
supporterror_InterfaceSupportsErrorInfo( ISupportErrorInfo
*iface
, REFIID riid
)
1396 static const struct ISupportErrorInfoVtbl support_error_vtbl
=
1398 supporterror_QueryInterface
,
1399 supporterror_AddRef
,
1400 supporterror_Release
,
1401 supporterror_InterfaceSupportsErrorInfo
1404 static void test_ConnectionPoint(void)
1409 IConnectionPoint
*point
;
1410 IConnectionPointContainer
*pointcontainer
;
1411 struct conn_event conn_event
= { { &conneventvt_vtbl
}, 0 };
1412 ISupportErrorInfo support_err_sink
= { &support_error_vtbl
};
1414 hr
= CoCreateInstance( &CLSID_Connection
, NULL
, CLSCTX_INPROC_SERVER
,
1415 &IID_IConnectionPointContainer
, (void**)&pointcontainer
);
1417 hr
= IConnectionPointContainer_FindConnectionPoint( pointcontainer
, &DIID_ConnectionEvents
, NULL
);
1418 ok( hr
== E_POINTER
, "got %08x\n", hr
);
1420 hr
= IConnectionPointContainer_FindConnectionPoint( pointcontainer
, &DIID_RecordsetEvents
, &point
);
1421 ok( hr
== CONNECT_E_NOCONNECTION
, "got %08x\n", hr
);
1423 hr
= IConnectionPointContainer_FindConnectionPoint( pointcontainer
, &DIID_ConnectionEvents
, &point
);
1424 ok( hr
== S_OK
, "got %08x\n", hr
);
1426 /* nothing advised yet */
1427 hr
= IConnectionPoint_Unadvise( point
, 3 );
1428 ok( hr
== E_FAIL
, "got %08x\n", hr
);
1430 hr
= IConnectionPoint_Advise( point
, NULL
, NULL
);
1431 ok( hr
== E_FAIL
, "got %08x\n", hr
);
1433 hr
= IConnectionPoint_Advise( point
, (void*)&conn_event
.conn_event_sink
, NULL
);
1434 ok( hr
== E_FAIL
, "got %08x\n", hr
);
1436 cookie
= 0xdeadbeef;
1437 hr
= IConnectionPoint_Advise( point
, NULL
, &cookie
);
1438 ok( hr
== E_FAIL
, "got %08x\n", hr
);
1439 ok( cookie
== 0xdeadbeef, "got %08x\n", cookie
);
1441 /* unsupported sink */
1442 cookie
= 0xdeadbeef;
1443 hr
= IConnectionPoint_Advise( point
, (void*)&support_err_sink
, &cookie
);
1444 ok( hr
== E_FAIL
, "got %08x\n", hr
);
1445 ok( !cookie
, "got %08x\n", cookie
);
1448 hr
= IConnectionPoint_Advise( point
, (void*)&conn_event
.conn_event_sink
, &cookie
);
1449 ok( hr
== S_OK
, "got %08x\n", hr
);
1450 ok( cookie
, "got %08x\n", cookie
);
1452 /* invalid cookie */
1453 hr
= IConnectionPoint_Unadvise( point
, 0 );
1454 ok( hr
== E_FAIL
, "got %08x\n", hr
);
1457 hr
= IConnectionPoint_Unadvise( point
, cookie
+ 1 );
1458 ok( hr
== E_FAIL
, "got %08x\n", hr
);
1460 hr
= IConnectionPoint_Unadvise( point
, cookie
);
1461 ok( hr
== S_OK
, "got %08x\n", hr
);
1463 /* sinks are released when the connection is destroyed */
1465 hr
= IConnectionPoint_Advise( point
, (void*)&conn_event
.conn_event_sink
, &cookie
);
1466 ok( hr
== S_OK
, "got %08x\n", hr
);
1467 ok( cookie
, "got %08x\n", cookie
);
1468 ok( conn_event
.refs
== 1, "got %d\n", conn_event
.refs
);
1470 refs
= IConnectionPoint_Release( point
);
1471 ok( refs
== 1, "got %u", refs
);
1473 IConnectionPointContainer_Release( pointcontainer
);
1475 ok( !conn_event
.refs
, "got %d\n", conn_event
.refs
);
1480 CoInitialize( NULL
);
1482 test_ADORecordsetConstruction();
1483 test_ConnectionPoint();