Commit ac23f2c8 authored by Robert Shearman's avatar Robert Shearman Committed by Alexandre Julliard

Add outer unknown support for typelib marshaler.

parent fb36140a
...@@ -355,6 +355,7 @@ typedef struct _TMProxyImpl { ...@@ -355,6 +355,7 @@ typedef struct _TMProxyImpl {
IRpcChannelBuffer* chanbuf; IRpcChannelBuffer* chanbuf;
IID iid; IID iid;
CRITICAL_SECTION crit; CRITICAL_SECTION crit;
IUnknown *outerunknown;
} TMProxyImpl; } TMProxyImpl;
static HRESULT WINAPI static HRESULT WINAPI
...@@ -1426,6 +1427,43 @@ xCall(LPVOID retptr, int method, TMProxyImpl *tpinfo /*, args */) ...@@ -1426,6 +1427,43 @@ xCall(LPVOID retptr, int method, TMProxyImpl *tpinfo /*, args */)
return status; return status;
} }
HRESULT WINAPI ProxyIUnknown_QueryInterface(IUnknown *iface, REFIID riid, void **ppv)
{
TMProxyImpl *proxy = (TMProxyImpl *)iface;
TRACE("(%s, %p)\n", debugstr_guid(riid), ppv);
if (proxy->outerunknown)
return IUnknown_QueryInterface(proxy->outerunknown, riid, ppv);
FIXME("No interface\n");
return E_NOINTERFACE;
}
ULONG WINAPI ProxyIUnknown_AddRef(IUnknown *iface)
{
TMProxyImpl *proxy = (TMProxyImpl *)iface;
TRACE("\n");
if (proxy->outerunknown)
return IUnknown_AddRef(proxy->outerunknown);
return 2; /* FIXME */
}
ULONG WINAPI ProxyIUnknown_Release(IUnknown *iface)
{
TMProxyImpl *proxy = (TMProxyImpl *)iface;
TRACE("\n");
if (proxy->outerunknown)
return IUnknown_Release(proxy->outerunknown);
return 1; /* FIXME */
}
static HRESULT WINAPI static HRESULT WINAPI
PSFacBuf_CreateProxy( PSFacBuf_CreateProxy(
LPPSFACTORYBUFFER iface, IUnknown* pUnkOuter, REFIID riid, LPPSFACTORYBUFFER iface, IUnknown* pUnkOuter, REFIID riid,
...@@ -1449,6 +1487,7 @@ PSFacBuf_CreateProxy( ...@@ -1449,6 +1487,7 @@ PSFacBuf_CreateProxy(
assert(sizeof(TMAsmProxy) == 12); assert(sizeof(TMAsmProxy) == 12);
proxy->outerunknown = pUnkOuter;
proxy->asmstubs = VirtualAlloc(NULL, sizeof(TMAsmProxy) * nroffuncs, MEM_COMMIT, PAGE_EXECUTE_READWRITE); proxy->asmstubs = VirtualAlloc(NULL, sizeof(TMAsmProxy) * nroffuncs, MEM_COMMIT, PAGE_EXECUTE_READWRITE);
if (!proxy->asmstubs) { if (!proxy->asmstubs) {
ERR("Could not commit pages for proxy thunks\n"); ERR("Could not commit pages for proxy thunks\n");
...@@ -1460,17 +1499,22 @@ PSFacBuf_CreateProxy( ...@@ -1460,17 +1499,22 @@ PSFacBuf_CreateProxy(
proxy->lpvtbl = HeapAlloc(GetProcessHeap(),0,sizeof(LPBYTE)*nroffuncs); proxy->lpvtbl = HeapAlloc(GetProcessHeap(),0,sizeof(LPBYTE)*nroffuncs);
for (i=0;i<nroffuncs;i++) { for (i=0;i<nroffuncs;i++) {
int nrofargs;
TMAsmProxy *xasm = proxy->asmstubs+i; TMAsmProxy *xasm = proxy->asmstubs+i;
/* nrofargs without This */
switch (i) { switch (i) {
case 0: nrofargs = 2; case 0:
proxy->lpvtbl[i] = ProxyIUnknown_QueryInterface;
break;
case 1:
proxy->lpvtbl[i] = ProxyIUnknown_AddRef;
break; break;
case 1: case 2: nrofargs = 0; case 2:
proxy->lpvtbl[i] = ProxyIUnknown_Release;
break; break;
default: { default: {
int j; int j;
/* nrofargs without This */
int nrofargs;
hres = _get_funcdesc(tinfo,i,&fdesc,NULL,NULL); hres = _get_funcdesc(tinfo,i,&fdesc,NULL,NULL);
if (hres) { if (hres) {
ERR("GetFuncDesc %lx should not fail here.\n",hres); ERR("GetFuncDesc %lx should not fail here.\n",hres);
...@@ -1485,9 +1529,6 @@ PSFacBuf_CreateProxy( ...@@ -1485,9 +1529,6 @@ PSFacBuf_CreateProxy(
ERR("calling convention is not stdcall????\n"); ERR("calling convention is not stdcall????\n");
return E_FAIL; return E_FAIL;
} }
break;
}
}
/* popl %eax - return ptr /* popl %eax - return ptr
* pushl <nr> * pushl <nr>
* pushl %eax * pushl %eax
...@@ -1497,16 +1538,19 @@ PSFacBuf_CreateProxy( ...@@ -1497,16 +1538,19 @@ PSFacBuf_CreateProxy(
* *
* arg3 arg2 arg1 <method> <returnptr> * arg3 arg2 arg1 <method> <returnptr>
*/ */
xasm->popleax = 0x58; xasm->popleax = 0x58;
xasm->pushlval = 0x6a; xasm->pushlval = 0x6a;
xasm->nr = i; xasm->nr = i;
xasm->pushleax = 0x50; xasm->pushleax = 0x50;
xasm->lcall = 0xe8; /* relative jump */ xasm->lcall = 0xe8; /* relative jump */
xasm->xcall = (DWORD)xCall; xasm->xcall = (DWORD)xCall;
xasm->xcall -= (DWORD)&(xasm->lret); xasm->xcall -= (DWORD)&(xasm->lret);
xasm->lret = 0xc2; xasm->lret = 0xc2;
xasm->bytestopop= (nrofargs+2)*4; /* pop args, This, iMethod */ xasm->bytestopop= (nrofargs+2)*4; /* pop args, This, iMethod */
proxy->lpvtbl[i] = xasm; proxy->lpvtbl[i] = xasm;
break;
}
}
} }
proxy->lpvtbl2 = &tmproxyvtable; proxy->lpvtbl2 = &tmproxyvtable;
/* 1 reference for the proxy and 1 for the object */ /* 1 reference for the proxy and 1 for the object */
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment