2 * Unit test suite for cstubs
4 * Copyright 2006 Huw Davies
6 * This library is free software; you can redistribute it and/or
7 * modify it under the terms of the GNU Lesser General Public
8 * License as published by the Free Software Foundation; either
9 * version 2.1 of the License, or (at your option) any later version.
11 * This library is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14 * Lesser General Public License for more details.
16 * You should have received a copy of the GNU Lesser General Public
17 * License along with this library; if not, write to the Free Software
18 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
23 #define PROXY_DELEGATION
26 #include "wine/test.h"
37 static CStdPSFactoryBuffer PSFactoryBuffer;
39 CSTDSTUBBUFFERRELEASE(&PSFactoryBuffer)
40 CSTDSTUBBUFFER2RELEASE(&PSFactoryBuffer)
42 static GUID IID_if1 = {0x12345678, 1234, 5678, {12,34,56,78,90,0xab,0xcd,0xef}};
43 static GUID IID_if2 = {0x12345679, 1234, 5678, {12,34,56,78,90,0xab,0xcd,0xef}};
44 static GUID IID_if3 = {0x1234567a, 1234, 5678, {12,34,56,78,90,0xab,0xcd,0xef}};
45 static GUID IID_if4 = {0x1234567b, 1234, 5678, {12,34,56,78,90,0xab,0xcd,0xef}};
47 static int my_alloc_called;
48 static int my_free_called;
50 static void * CALLBACK my_alloc(size_t size)
53 return NdrOleAllocate(size);
56 static void CALLBACK my_free(void *ptr)
59 return NdrOleFree(ptr);
62 typedef struct _MIDL_PROC_FORMAT_STRING
65 unsigned char Format[ 2 ];
66 } MIDL_PROC_FORMAT_STRING;
68 typedef struct _MIDL_TYPE_FORMAT_STRING
71 unsigned char Format[ 2 ];
72 } MIDL_TYPE_FORMAT_STRING;
75 static const MIDL_PROC_FORMAT_STRING __MIDL_ProcFormatString =
83 static const MIDL_TYPE_FORMAT_STRING __MIDL_TypeFormatString =
91 static const MIDL_STUB_DESC Object_StubDesc =
101 __MIDL_TypeFormatString.Format,
102 1, /* -error bounds_check flag */
103 0x20000, /* Ndr library version */
105 0x50100a4, /* MIDL Version 5.1.164 */
108 0, /* notify & notify_flag routine table */
115 HRESULT WINAPI if1_fn1_Proxy(void *This)
120 void __RPC_STUB if1_fn1_Stub(
121 IRpcStubBuffer *This,
122 IRpcChannelBuffer *_pRpcChannelBuffer,
123 PRPC_MESSAGE _pRpcMessage,
124 DWORD *_pdwStubPhase)
129 HRESULT WINAPI if1_fn2_Proxy(void *This)
134 void __RPC_STUB if1_fn2_Stub(
135 IRpcStubBuffer *This,
136 IRpcChannelBuffer *_pRpcChannelBuffer,
137 PRPC_MESSAGE _pRpcMessage,
138 DWORD *_pdwStubPhase)
143 CINTERFACE_PROXY_VTABLE(5) if1_proxy_vtbl =
146 { IUnknown_QueryInterface_Proxy,
147 IUnknown_AddRef_Proxy,
148 IUnknown_Release_Proxy ,
155 static const unsigned short if1_FormatStringOffsetTable[] =
161 static const MIDL_SERVER_INFO if1_server_info =
165 __MIDL_ProcFormatString.Format,
166 &if1_FormatStringOffsetTable[-3],
173 static const PRPC_STUB_FUNCTION if1_table[] =
179 CInterfaceStubVtbl if1_stub_vtbl =
187 { CStdStubBuffer_METHODS }
190 CINTERFACE_PROXY_VTABLE(13) if2_proxy_vtbl =
193 { IUnknown_QueryInterface_Proxy,
194 IUnknown_AddRef_Proxy,
195 IUnknown_Release_Proxy ,
209 static const unsigned short if2_FormatStringOffsetTable[] =
224 static const MIDL_SERVER_INFO if2_server_info =
228 __MIDL_ProcFormatString.Format,
229 &if2_FormatStringOffsetTable[-3],
236 static const PRPC_STUB_FUNCTION if2_table[] =
238 STUB_FORWARDING_FUNCTION,
239 STUB_FORWARDING_FUNCTION,
240 STUB_FORWARDING_FUNCTION,
241 STUB_FORWARDING_FUNCTION,
242 STUB_FORWARDING_FUNCTION,
243 STUB_FORWARDING_FUNCTION,
244 STUB_FORWARDING_FUNCTION,
245 STUB_FORWARDING_FUNCTION,
246 STUB_FORWARDING_FUNCTION,
247 STUB_FORWARDING_FUNCTION
250 CInterfaceStubVtbl if2_stub_vtbl =
258 { CStdStubBuffer_DELEGATING_METHODS }
261 CINTERFACE_PROXY_VTABLE(4) if3_proxy_vtbl =
264 { IUnknown_QueryInterface_Proxy,
265 IUnknown_AddRef_Proxy,
266 IUnknown_Release_Proxy ,
272 static const unsigned short if3_FormatStringOffsetTable[] =
278 static const MIDL_SERVER_INFO if3_server_info =
282 __MIDL_ProcFormatString.Format,
283 &if3_FormatStringOffsetTable[-3],
290 static const PRPC_STUB_FUNCTION if3_table[] =
295 CInterfaceStubVtbl if3_stub_vtbl =
303 { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }
306 CINTERFACE_PROXY_VTABLE(7) if4_proxy_vtbl =
309 { IUnknown_QueryInterface_Proxy,
310 IUnknown_AddRef_Proxy,
311 IUnknown_Release_Proxy ,
319 static const unsigned short if4_FormatStringOffsetTable[] =
328 static const MIDL_SERVER_INFO if4_server_info =
332 __MIDL_ProcFormatString.Format,
333 &if4_FormatStringOffsetTable[-3],
340 static const PRPC_STUB_FUNCTION if4_table[] =
342 STUB_FORWARDING_FUNCTION,
343 STUB_FORWARDING_FUNCTION,
344 STUB_FORWARDING_FUNCTION,
345 STUB_FORWARDING_FUNCTION,
348 CInterfaceStubVtbl if4_stub_vtbl =
356 { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }
359 const CInterfaceProxyVtbl *cstub_ProxyVtblList[] =
361 (const CInterfaceProxyVtbl *) &if1_proxy_vtbl,
362 (const CInterfaceProxyVtbl *) &if2_proxy_vtbl,
363 (const CInterfaceProxyVtbl *) &if3_proxy_vtbl,
364 (const CInterfaceProxyVtbl *) &if4_proxy_vtbl,
368 const CInterfaceStubVtbl *cstub_StubVtblList[] =
370 (const CInterfaceStubVtbl *) &if1_stub_vtbl,
371 (const CInterfaceStubVtbl *) &if2_stub_vtbl,
372 (const CInterfaceStubVtbl *) &if3_stub_vtbl,
373 (const CInterfaceStubVtbl *) &if4_stub_vtbl,
377 PCInterfaceName const if_name_list[] =
386 const IID *base_iid_list[] =
395 #define cstub_CHECK_IID(n) IID_GENERIC_CHECK_IID( cstub, pIID, n)
397 int __stdcall iid_lookup( const IID * pIID, int * pIndex )
401 IID_BS_LOOKUP_INITIAL_TEST( cstub, 4, 4 )
402 IID_BS_LOOKUP_NEXT_TEST( cstub, 2 )
403 IID_BS_LOOKUP_NEXT_TEST( cstub, 1 )
404 IID_BS_LOOKUP_RETURN_RESULT( cstub, 4, *pIndex )
409 const ExtendedProxyFileInfo my_proxy_file_info =
411 (const PCInterfaceProxyVtblList *) &cstub_ProxyVtblList,
412 (const PCInterfaceStubVtblList *) &cstub_StubVtblList,
413 (const PCInterfaceName *) &if_name_list,
414 (const IID **) &base_iid_list,
424 const ProxyFileInfo *proxy_file_list[] = {
430 static IPSFactoryBuffer *test_NdrDllGetClassObject(void)
432 IPSFactoryBuffer *ppsf = NULL;
433 const CLSID PSDispatch = {0x20420, 0, 0, {0xc0, 0, 0, 0, 0, 0, 0, 0x46}};
435 HMODULE hmod = LoadLibraryA("rpcrt4.dll");
436 void *CStd_QueryInterface = GetProcAddress(hmod, "CStdStubBuffer_QueryInterface");
437 void *CStd_AddRef = GetProcAddress(hmod, "CStdStubBuffer_AddRef");
438 void *CStd_Release = GetProcAddress(hmod, "NdrCStdStubBuffer_Release");
439 void *CStd_Connect = GetProcAddress(hmod, "CStdStubBuffer_Connect");
440 void *CStd_Disconnect = GetProcAddress(hmod, "CStdStubBuffer_Disconnect");
441 void *CStd_Invoke = GetProcAddress(hmod, "CStdStubBuffer_Invoke");
442 void *CStd_IsIIDSupported = GetProcAddress(hmod, "CStdStubBuffer_IsIIDSupported");
443 void *CStd_CountRefs = GetProcAddress(hmod, "CStdStubBuffer_CountRefs");
444 void *CStd_DebugServerQueryInterface = GetProcAddress(hmod, "CStdStubBuffer_DebugServerQueryInterface");
445 void *CStd_DebugServerRelease = GetProcAddress(hmod, "CStdStubBuffer_DebugServerRelease");
447 r = NdrDllGetClassObject(&PSDispatch, &IID_IPSFactoryBuffer, (void**)&ppsf, proxy_file_list,
448 &PSDispatch, &PSFactoryBuffer);
450 ok(r == S_OK, "ret %08lx\n", r);
451 ok(ppsf != NULL, "ppsf == NULL\n");
453 ok(PSFactoryBuffer.pProxyFileList == proxy_file_list, "pfl not the same\n");
454 ok(PSFactoryBuffer.pProxyFileList[0]->pStubVtblList == (PCInterfaceStubVtblList *) &cstub_StubVtblList, "stub vtbllist not the same\n");
456 /* if1 is non-delegating, if2 is delegating, if3 is non-delegating
457 but I've zero'ed the vtbl entries, similarly if4 is delegating
458 with zero'ed vtbl entries */
460 #define VTBL_TEST_NOT_CHANGE_TO(name, i) \
461 ok(PSFactoryBuffer.pProxyFileList[0]->pStubVtblList[i]->Vtbl.name != CStd_##name, #name "vtbl %d updated %p %p\n", \
462 i, PSFactoryBuffer.pProxyFileList[0]->pStubVtblList[i]->Vtbl.name, CStd_##name );
463 #define VTBL_TEST_CHANGE_TO(name, i) \
464 ok(PSFactoryBuffer.pProxyFileList[0]->pStubVtblList[i]->Vtbl.name == CStd_##name, #name "vtbl %d not updated %p %p\n", \
465 i, PSFactoryBuffer.pProxyFileList[0]->pStubVtblList[i]->Vtbl.name, CStd_##name );
466 #define VTBL_TEST_ZERO(name, i) \
467 ok(PSFactoryBuffer.pProxyFileList[0]->pStubVtblList[i]->Vtbl.name == NULL, #name "vtbl %d not null %p\n", \
468 i, PSFactoryBuffer.pProxyFileList[0]->pStubVtblList[i]->Vtbl.name );
469 VTBL_TEST_NOT_CHANGE_TO(QueryInterface, 0);
470 VTBL_TEST_NOT_CHANGE_TO(AddRef, 0);
471 VTBL_TEST_NOT_CHANGE_TO(Release, 0);
472 VTBL_TEST_NOT_CHANGE_TO(Connect, 0);
473 VTBL_TEST_NOT_CHANGE_TO(Disconnect, 0);
474 VTBL_TEST_NOT_CHANGE_TO(Invoke, 0);
475 VTBL_TEST_NOT_CHANGE_TO(IsIIDSupported, 0);
476 VTBL_TEST_NOT_CHANGE_TO(CountRefs, 0);
477 VTBL_TEST_NOT_CHANGE_TO(DebugServerQueryInterface, 0);
478 VTBL_TEST_NOT_CHANGE_TO(DebugServerRelease, 0);
480 VTBL_TEST_CHANGE_TO(QueryInterface, 1);
481 VTBL_TEST_CHANGE_TO(AddRef, 1);
482 VTBL_TEST_NOT_CHANGE_TO(Release, 1);
484 VTBL_TEST_NOT_CHANGE_TO(Connect, 1);
485 VTBL_TEST_NOT_CHANGE_TO(Disconnect, 1);
487 VTBL_TEST_CHANGE_TO(Invoke, 1);
488 VTBL_TEST_CHANGE_TO(IsIIDSupported, 1);
490 VTBL_TEST_NOT_CHANGE_TO(CountRefs, 1);
492 VTBL_TEST_CHANGE_TO(DebugServerQueryInterface, 1);
493 VTBL_TEST_CHANGE_TO(DebugServerRelease, 1);
495 VTBL_TEST_CHANGE_TO(QueryInterface, 2);
496 VTBL_TEST_CHANGE_TO(AddRef, 2);
497 VTBL_TEST_ZERO(Release, 2);
498 VTBL_TEST_CHANGE_TO(Connect, 2);
499 VTBL_TEST_CHANGE_TO(Disconnect, 2);
500 VTBL_TEST_CHANGE_TO(Invoke, 2);
501 VTBL_TEST_CHANGE_TO(IsIIDSupported, 2);
502 VTBL_TEST_CHANGE_TO(CountRefs, 2);
503 VTBL_TEST_CHANGE_TO(DebugServerQueryInterface, 2);
504 VTBL_TEST_CHANGE_TO(DebugServerRelease, 2);
506 VTBL_TEST_CHANGE_TO(QueryInterface, 3);
507 VTBL_TEST_CHANGE_TO(AddRef, 3);
508 VTBL_TEST_ZERO(Release, 3);
510 VTBL_TEST_NOT_CHANGE_TO(Connect, 3);
511 VTBL_TEST_NOT_CHANGE_TO(Disconnect, 3);
513 VTBL_TEST_CHANGE_TO(Invoke, 3);
514 VTBL_TEST_CHANGE_TO(IsIIDSupported, 3);
516 VTBL_TEST_NOT_CHANGE_TO(CountRefs, 3);
518 VTBL_TEST_CHANGE_TO(DebugServerQueryInterface, 3);
519 VTBL_TEST_CHANGE_TO(DebugServerRelease, 3);
523 #undef VTBL_TEST_NOT_CHANGE_TO
524 #undef VTBL_TEST_CHANGE_TO
525 #undef VTBL_TEST_ZERO
527 ok(PSFactoryBuffer.RefCount == 1, "ref count %ld\n", PSFactoryBuffer.RefCount);
531 static int base_buffer_invoke_called;
532 static HRESULT WINAPI base_buffer_Invoke(IRpcStubBuffer *This, RPCOLEMESSAGE *msg, IRpcChannelBuffer *channel)
534 base_buffer_invoke_called++;
535 ok(msg == (RPCOLEMESSAGE*)0xcafebabe, "msg ptr changed\n");
536 ok(channel == (IRpcChannelBuffer*)0xdeadbeef, "channel ptr changed\n");
537 return S_OK; /* returning any failure here results in an exception */
540 static IRpcStubBufferVtbl base_buffer_vtbl = {
553 static void test_NdrStubForwardingFunction(void)
557 IRpcChannelBuffer *channel = (IRpcChannelBuffer*)0xdeadbeef;
558 RPC_MESSAGE *msg = (RPC_MESSAGE*)0xcafebabe;
559 DWORD *phase = (DWORD*)0x12345678;
560 IRpcStubBufferVtbl *base_buffer_vtbl_ptr = &base_buffer_vtbl;
561 IRpcStubBuffer *base_stub_buffer = (IRpcStubBuffer*)&base_buffer_vtbl_ptr;
563 memset(This, 0xcc, sizeof(This));
564 This[0] = base_stub_buffer;
565 real_this = &This[1];
567 NdrStubForwardingFunction( real_this, channel, msg, phase );
570 ok(base_buffer_invoke_called == 1, "base_buffer_invoke called %d times\n", base_buffer_invoke_called);
575 static IRpcStubBuffer *create_stub(IPSFactoryBuffer *ppsf, REFIID iid, IUnknown *obj, HRESULT expected_result)
577 IRpcStubBuffer *pstub = NULL;
580 r = IPSFactoryBuffer_CreateStub(ppsf, iid, obj, &pstub);
581 ok(r == expected_result, "CreateStub returned %08lx expected %08lx\n", r, expected_result);
585 static HRESULT WINAPI create_stub_test_QI(IUnknown *This, REFIID iid, void **ppv)
587 ok(IsEqualIID(iid, &IID_if1), "incorrect iid\n");
588 *ppv = (void*)0xdeadbeef;
592 static IUnknownVtbl create_stub_test_vtbl =
599 static HRESULT WINAPI create_stub_test_fail_QI(IUnknown *This, REFIID iid, void **ppv)
601 ok(IsEqualIID(iid, &IID_if1), "incorrect iid\n");
603 return E_NOINTERFACE;
606 static IUnknownVtbl create_stub_test_fail_vtbl =
608 create_stub_test_fail_QI,
613 static void test_CreateStub(IPSFactoryBuffer *ppsf)
615 IUnknownVtbl *vtbl = &create_stub_test_vtbl;
616 IUnknown *obj = (IUnknown*)&vtbl;
617 IRpcStubBuffer *pstub = create_stub(ppsf, &IID_if1, obj, S_OK);
618 CStdStubBuffer *cstd_stub = (CStdStubBuffer*)pstub;
619 CInterfaceStubHeader *header = ((CInterfaceStubHeader *)cstd_stub->lpVtbl) - 1;
621 ok(IsEqualIID(header->piid, &IID_if1), "header iid differs\n");
622 ok(cstd_stub->RefCount == 1, "ref count %ld\n", cstd_stub->RefCount);
623 /* 0xdeadbeef returned from create_stub_test_QI */
624 ok(cstd_stub->pvServerObject == (void*)0xdeadbeef, "pvServerObject %p", cstd_stub->pvServerObject);
625 ok(cstd_stub->pPSFactory == ppsf, "pPSFactory %p\n", cstd_stub->pPSFactory);
627 vtbl = &create_stub_test_fail_vtbl;
628 pstub = create_stub(ppsf, &IID_if1, obj, E_NOINTERFACE);
634 IPSFactoryBuffer *ppsf;
638 ppsf = test_NdrDllGetClassObject();
639 test_NdrStubForwardingFunction();
640 test_CreateStub(ppsf);