Is there any chance of help here, please.
For one reason or another I need to help get the ole32/oleaut32/rpcrt4 working for our application (the REG_EXPAND_SZ issue means that we don't work with wine after 200409 because of the mix of native dlls we use)
I just tried running with the native ole32/oleaut32/rpcrt4 and the first thing I tripped over was (what I presume is) an out-of-process COM problem.
The actual stack dump is that: _LocalServerThread (compobj.c) calls StdMarshalImpl_MarshalInterface (...) which has mid.oxid = COM_CurrentApt()->oxid; which throws a memory error because COM_CurrentApt is null because, presumably the thread hasn't yet initialised an apartment.
Does anyone know anything about this? e.g. when starting a new thread where does the apartment get initialized?
On Fri, 17 Dec 2004 10:49:45 -0800, Bill Medland wrote:
Does anyone know anything about this? e.g. when starting a new thread where does the apartment get initialized?
It's supposed to get initialized in the call to CoInitialize[Ex] however the _LocalServerThread never calls this as it's an internal implementation detail of out of process DCOM.
This looks like we haven't got the design quite right here, the LocalServerThread doesn't exist in native DCOM as far as I can tell so it may need to be replaced by something else.
The code in StdMarshalImpl is correct, the problem is that the local server thread is violating the COM laws by using CoMarshalInterface before entering an apartment.
For now, does this patch help?
Index: dlls/ole32/compobj.c =================================================================== RCS file: /home/wine/wine/dlls/ole32/compobj.c,v retrieving revision 1.113 diff -u -p -r1.113 compobj.c --- dlls/ole32/compobj.c 14 Dec 2004 15:28:58 -0000 1.113 +++ dlls/ole32/compobj.c 17 Dec 2004 19:13:22 -0000 @@ -102,6 +102,7 @@ typedef struct tagRegisteredClass DWORD connectFlags; DWORD dwCookie; HANDLE hThread; /* only for localserver */ + APARTMENT *apt; /* owning apartment */ struct tagRegisteredClass* nextClass; } RegisteredClass;
@@ -1107,6 +1108,13 @@ _LocalServerThread(LPVOID param) {
TRACE("Starting threader for %s.\n",debugstr_guid(&newClass->classIdentifier));
+ /* we need to enter the apartment of the thread which registered + * the class object to perform the next stage + */ + + assert( newClass->apt ); + NtCurrentTeb()->ReservedForOle = newClass->apt; + strcpy(pipefn,PIPEPREF); WINE_StringFromCLSID(&newClass->classIdentifier,pipefn+strlen(PIPEPREF));
@@ -1219,6 +1227,12 @@ HRESULT WINAPI CoRegisterClassObject( if ( (lpdwRegister==0) || (pUnk==0) ) return E_INVALIDARG;
+ if (!COM_CurrentApt()) + { + ERR("COM was not initialized\n"); + return CO_E_NOTINITIALIZED; + } + *lpdwRegister = 0;
/* @@ -1240,6 +1254,7 @@ HRESULT WINAPI CoRegisterClassObject( newClass->classIdentifier = *rclsid; newClass->runContext = dwClsContext; newClass->connectFlags = flags; + newClass->apt = COM_CurrentApt(); /* * Use the address of the chain node as the cookie since we are sure it's * unique.
On December 17, 2004 11:18 am, Mike Hearn wrote:
Thanks Mike
On Fri, 17 Dec 2004 10:49:45 -0800, Bill Medland wrote:
Does anyone know anything about this? e.g. when starting a new thread where does the apartment get initialized?
It's supposed to get initialized in the call to CoInitialize[Ex] however the _LocalServerThread never calls this as it's an internal implementation detail of out of process DCOM.
This looks like we haven't got the design quite right here, the LocalServerThread doesn't exist in native DCOM as far as I can tell so it may need to be replaced by something else.
The code in StdMarshalImpl is correct, the problem is that the local server thread is violating the COM laws by using CoMarshalInterface before entering an apartment.
For now, does this patch help?
Well, it gets me past the illegal memory reference; I can start looking at what else failed now.
On Fri, 17 Dec 2004 13:34:53 -0800, Bill Medland wrote:
Well, it gets me past the illegal memory reference; I can start looking at what else failed now.
In case you aren't already aware, Rob and I are doing a lot of work in this area currently. If you want to pool resources that'd be good. Posting a +ole trace of the failing app would be a good start.
thanks -mike
On December 17, 2004 01:56 pm, Mike Hearn wrote:
On Fri, 17 Dec 2004 13:34:53 -0800, Bill Medland wrote:
Well, it gets me past the illegal memory reference; I can start looking at what else failed now.
In case you aren't already aware, Rob and I are doing a lot of work in this area currently. If you want to pool resources that'd be good. Posting a +ole trace of the failing app would be a good start.
thanks -mike
Pooling would be good. I'll help as much as I can.
To start with, here's the relevant part of the trace.
trace:ole:WINE_StringFromCLSID 0x456ed8->{B6B35894-DD6F-11D3-84AC-00C04F0E1B46} trace:ole:CoGetClassObject CLSID: {b6b35894-dd6f-11d3-84ac-00c04f0e1b46}, IID: {00000001-0000-0000-c000-000000000046} warn:ole:CoGetClassObject class {B6B35894-DD6F-11D3-84AC-00C04F0E1B46} not registered inproc trace:ole:create_marshalled_proxy rclsid={b6b35894-dd6f-11d3-84ac-00c04f0e1b46}, iid={00000001-0000-0000-c000-000000000046} trace:ole:WINE_StringFromCLSID 0x456ed8->{B6B35894-DD6F-11D3-84AC-00C04F0E1B46} trace:ole:WINE_StringFromCLSID 0x456ed8->{B6B35894-DD6F-11D3-84AC-00C04F0E1B46} trace:ole:create_server activating local server 'L"G:\runtime\a4wsignonmgr.exe -Embedding"' for {B6B35894-DD6F-11D3-84AC-00C04F0E1B46} trace:ole:DllMain 0x409e0000 0x1 0x1 warn:ole:create_marshalled_proxy Could not open named pipe to broker \.\pipe{B6B35894-DD6F-11D3-84AC-00C04F0E1B46}, le is 2 trace:ole:DllMain (0x40ab0000,1,0x1) trace:ole:CoInitializeEx ((nil), 2) trace:ole:CoInitializeEx () - Initializing the COM libraries trace:ole:RunningObjectTableImpl_Initialize () trace:ole:WINE_StringFromCLSID 0x41f320->{A2086A6A-3F3E-457C-8102-A4F99AD7C2DA} trace:ole:CoRegisterClassObject ({b6b35894-dd6f-11d3-84ac-00c04f0e1b46},0x42130170,0x00000004,0x00000001,0x41f094) trace:ole:listener_thread Process listener thread starting on (\.\pipe\WINE_OLE_StubMgr_00000010) warn:ole:create_marshalled_proxy Could not open named pipe to broker \.\pipe{B6B35894-DD6F-11D3-84AC-00C04F0E1B46}, le is 2 warn:ole:create_marshalled_proxy Could not open named pipe to broker \.\pipe{B6B35894-DD6F-11D3-84AC-00C04F0E1B46}, le is 2 trace:ole:_LocalServerThread Starting threader for {b6b35894-dd6f-11d3-84ac-00c04f0e1b46}. trace:ole:WINE_StringFromCLSID 0x40246118->{B6B35894-DD6F-11D3-84AC-00C04F0E1B46} trace:ole:_LocalServerThread marshalling IClassFactory to client trace:ole:CoMarshalInterface (0x40237280, {00000001-0000-0000-c000-000000000046}, 0x42130170, 0, (nil), 0) trace:ole:CoGetStandardMarshal ({00000001-0000-0000-c000-000000000046},0x42130170,0,(nil),0,0x42641fd0) trace:ole:CoMarshalInterface Using standard marshaling trace:ole:CoMarshalInterface Calling IMarshal::MarshalInterace trace:ole:StdMarshalImpl_MarshalInterface (...,{00000001-0000-0000-c000-000000000046},...) trace:ole:CoGetPSClsid () riid={00000001-0000-0000-c000-000000000046}, pclsid=0x42641f64 trace:ole:WINE_StringFromCLSID 0x40a23274->{00000001-0000-0000-C000-000000000046} trace:ole:__CLSIDFromStringA {00000320-0000-0000-C000-000000000046} -> 0x42641f64 trace:ole:CoGetPSClsid () Returning CLSID={00000320-0000-0000-c000-000000000046} trace:ole:WINE_StringFromCLSID 0x42641f64->{00000320-0000-0000-C000-000000000046} trace:ole:CoGetClassObject CLSID: {00000320-0000-0000-c000-000000000046}, IID: {d5f569d0-593b-101a-b569-08002b2dbf7a} trace:ole:COMPOBJ_DLLList_Add trace:ole:PSFacBuf_CreateStub ({00000001-0000-0000-c000-000000000046},0x42130170,0x42641f50) trace:ole:CoUnmarshalInterface (0x4025a778, {00000001-0000-0000-c000-000000000046}, 0x406ef5dc) trace:ole:get_unmarshaler_from_stream Using standard unmarshaling trace:ole:StdMarshalImpl_UnmarshalInterface (...,{00000001-0000-0000-c000-000000000046},....) trace:ole:CoGetPSClsid () riid={00000001-0000-0000-c000-000000000046}, pclsid=0x406ef0d8 trace:ole:WINE_StringFromCLSID 0x409a5274->{00000001-0000-0000-C000-000000000046} trace:ole:__CLSIDFromStringA {00000320-0000-0000-C000-000000000046} -> 0x406ef0d8 trace:ole:CoGetPSClsid () Returning CLSID={00000320-0000-0000-c000-000000000046} trace:ole:WINE_StringFromCLSID 0x406ef0d8->{00000320-0000-0000-C000-000000000046} trace:ole:CoGetClassObject CLSID: {00000320-0000-0000-c000-000000000046}, IID: {d5f569d0-593b-101a-b569-08002b2dbf7a} trace:ole:COMPOBJ_DLLList_Add trace:ole:_LocalServerThread done marshalling IClassFactory fixme:ole:PIPE_GetNewPipeBuf Could not open named pipe \.\pipe\WINE_OLE_StubMgr_0000001000000011, le is 2 err:ole:StdMarshalImpl_UnmarshalInterface Failed to get an rpc channel buffer for {00000001-0000-0000-c000-000000000046} err:ole:CoUnmarshalInterface IMarshal::UnmarshalInterface failed, 0x80004005 fixme:ole:CoCreateInstance no classfactory created for CLSID {b6b35894-dd6f-11d3-84ac-00c04f0e1b46}, hres is 0x80004005
Does anything jump out at you?
(Ill get started on the learning curve)
On Fri, 17 Dec 2004 14:27:30 -0800, Bill Medland wrote:
Does anything jump out at you?
(Ill get started on the learning curve)
Well, the error messages describe what's going on. The question is, why? I clearly need to resurrect my out of process COM test program and make it a part of the test suite.
BTW a +tid,+ole trace would be useful too, sorry I forgot about +tid before but it's really invaluable with DCOM stuff.
thanks -mike
On Fri, 17 Dec 2004 14:27:30 -0800, Bill Medland wrote:
fixme:ole:PIPE_GetNewPipeBuf Could not open named pipe \.\pipe\WINE_OLE_StubMgr_0000001000000011, le is 2
I see the problem. The patch which switched us over to using OXIDs isn't complete, the listener_thread should be per-apartment not per-process, and the pipe it creates should therefore use the oxid >> 32 + oxid string formatter.
Rob is travelling back to the UK today. I don't know when he'll be back online, or even if he'll be working over the Christmas period. If not I'll see if I can write a patch to fix this regression this weekend.
thanks -mike
Bill Medland wrote:
On December 17, 2004 01:56 pm, Mike Hearn wrote:
On Fri, 17 Dec 2004 13:34:53 -0800, Bill Medland wrote:
Well, it gets me past the illegal memory reference; I can start looking at what else failed now.
In case you aren't already aware, Rob and I are doing a lot of work in this area currently. If you want to pool resources that'd be good. Posting a +ole trace of the failing app would be a good start.
thanks -mike
Pooling would be good. I'll help as much as I can.
To start with, here's the relevant part of the trace.
trace:ole:WINE_StringFromCLSID 0x456ed8->{B6B35894-DD6F-11D3-84AC-00C04F0E1B46} trace:ole:CoGetClassObject CLSID: {b6b35894-dd6f-11d3-84ac-00c04f0e1b46}, IID: {00000001-0000-0000-c000-000000000046} warn:ole:CoGetClassObject class {B6B35894-DD6F-11D3-84AC-00C04F0E1B46} not registered inproc trace:ole:create_marshalled_proxy rclsid={b6b35894-dd6f-11d3-84ac-00c04f0e1b46}, iid={00000001-0000-0000-c000-000000000046} trace:ole:WINE_StringFromCLSID 0x456ed8->{B6B35894-DD6F-11D3-84AC-00C04F0E1B46} trace:ole:WINE_StringFromCLSID 0x456ed8->{B6B35894-DD6F-11D3-84AC-00C04F0E1B46} trace:ole:create_server activating local server 'L"G:\runtime\a4wsignonmgr.exe -Embedding"' for {B6B35894-DD6F-11D3-84AC-00C04F0E1B46} trace:ole:DllMain 0x409e0000 0x1 0x1 warn:ole:create_marshalled_proxy Could not open named pipe to broker \.\pipe{B6B35894-DD6F-11D3-84AC-00C04F0E1B46}, le is 2 trace:ole:DllMain (0x40ab0000,1,0x1) trace:ole:CoInitializeEx ((nil), 2) trace:ole:CoInitializeEx () - Initializing the COM libraries trace:ole:RunningObjectTableImpl_Initialize () trace:ole:WINE_StringFromCLSID 0x41f320->{A2086A6A-3F3E-457C-8102-A4F99AD7C2DA} trace:ole:CoRegisterClassObject ({b6b35894-dd6f-11d3-84ac-00c04f0e1b46},0x42130170,0x00000004,0x00000001,0x41f094) trace:ole:listener_thread Process listener thread starting on (\.\pipe\WINE_OLE_StubMgr_00000010)
Here's an untested patch. Let me know if it works.
Rob
On December 18, 2004 05:03 am, Robert Shearman wrote:
Bill Medland wrote:
On December 17, 2004 01:56 pm, Mike Hearn wrote:
On Fri, 17 Dec 2004 13:34:53 -0800, Bill Medland wrote:
Well, it gets me past the illegal memory reference; I can start looking at what else failed now.
In case you aren't already aware, Rob and I are doing a lot of work in this area currently. If you want to pool resources that'd be good. Posting a +ole trace of the failing app would be a good start.
thanks -mike
Pooling would be good. I'll help as much as I can.
CUT
Here's an untested patch. Let me know if it works.
Rob
If I combine it with Mike's patch I get the same null-Apt problem at a later point in the marshaling; I can give you a trace and bt if you want
If I combine it with Rob's CoInitializeEx patch rather than Mike's then it executes but still fails, as follows:
0009:trace:ole:WINE_StringFromCLSID 0x456ed8->{B6B35894-DD6F-11D3-84AC-00C04F0E1B46} 0009:trace:ole:CoGetClassObject CLSID: {b6b35894-dd6f-11d3-84ac-00c04f0e1b46}, IID: {00000001-0000-0000-c000-000000000046} 0009:warn:ole:CoGetClassObject class {B6B35894-DD6F-11D3-84AC-00C04F0E1B46} not registered inproc 0009:trace:ole:create_marshalled_proxy rclsid={b6b35894-dd6f-11d3-84ac-00c04f0e1b46}, iid={00000001-0000-0000-c000-000000000046} 0009:trace:ole:WINE_StringFromCLSID 0x456ed8->{B6B35894-DD6F-11D3-84AC-00C04F0E1B46} 0009:trace:ole:WINE_StringFromCLSID 0x456ed8->{B6B35894-DD6F-11D3-84AC-00C04F0E1B46} 0009:trace:ole:create_server activating local server 'L"G:\runtime\a4wsignonmgr.exe -Embedding"' for {B6B35894-DD6F-11D3-84AC-00C04F0E1B46} 0011:trace:ole:DllMain 0x409e0000 0x1 0x1 0009:warn:ole:create_marshalled_proxy Could not open named pipe to broker \.\pipe{B6B35894-DD6F-11D3-84AC-00C04F0E1B46}, le is 2 0011:trace:ole:DllMain (0x40ab0000,1,0x1) 0011:trace:ole:CoInitializeEx ((nil), 2) 0011:trace:ole:CoInitializeEx () - Initializing the COM libraries 0011:trace:ole:RunningObjectTableImpl_Initialize () 0011:trace:ole:WINE_StringFromCLSID 0x41f320->{A2086A6A-3F3E-457C-8102-A4F99AD7C2DA} 0011:trace:ole:CoRegisterClassObject ({b6b35894-dd6f-11d3-84ac-00c04f0e1b46},0x42130180,0x00000004,0x00000001,0x41f094) 0013:trace:ole:listener_thread Process listener thread starting on (\.\pipe\WINE_OLE_StubMgr_0000001000000011) 0009:warn:ole:create_marshalled_proxy Could not open named pipe to broker \.\pipe{B6B35894-DD6F-11D3-84AC-00C04F0E1B46}, le is 2 0009:warn:ole:create_marshalled_proxy Could not open named pipe to broker \.\pipe{B6B35894-DD6F-11D3-84AC-00C04F0E1B46}, le is 2 0014:trace:ole:_LocalServerThread Starting threader for {b6b35894-dd6f-11d3-84ac-00c04f0e1b46}. 0014:trace:ole:CoInitializeEx ((nil), 2) 0014:trace:ole:WINE_StringFromCLSID 0x40246118->{B6B35894-DD6F-11D3-84AC-00C04F0E1B46} 0014:trace:ole:_LocalServerThread marshalling IClassFactory to client 0014:trace:ole:CoMarshalInterface (0x40237280, {00000001-0000-0000-c000-000000000046}, 0x42130180, 0, (nil), 0) 0014:trace:ole:CoGetStandardMarshal ({00000001-0000-0000-c000-000000000046},0x42130180,0,(nil),0,0x42641fd0) 0014:trace:ole:CoMarshalInterface Using standard marshaling 0014:trace:ole:CoMarshalInterface Calling IMarshal::MarshalInterace 0014:trace:ole:StdMarshalImpl_MarshalInterface (...,{00000001-0000-0000-c000-000000000046},...) 0014:trace:ole:CoGetPSClsid () riid={00000001-0000-0000-c000-000000000046}, pclsid=0x42641f64 0014:trace:ole:WINE_StringFromCLSID 0x40a221b4->{00000001-0000-0000-C000-000000000046} 0014:trace:ole:__CLSIDFromStringA {00000320-0000-0000-C000-000000000046} -> 0x42641f64 0014:trace:ole:CoGetPSClsid () Returning CLSID={00000320-0000-0000-c000-000000000046} 0014:trace:ole:WINE_StringFromCLSID 0x42641f64->{00000320-0000-0000-C000-000000000046} 0014:trace:ole:CoGetClassObject CLSID: {00000320-0000-0000-c000-000000000046}, IID: {d5f569d0-593b-101a-b569-08002b2dbf7a} 0014:trace:ole:COMPOBJ_DLLList_Add 0014:trace:ole:PSFacBuf_CreateStub ({00000001-0000-0000-c000-000000000046},0x42130180,0x42641f50) 0009:trace:ole:CoUnmarshalInterface (0x40246d28, {00000001-0000-0000-c000-000000000046}, 0x406ef5dc) 0009:trace:ole:get_unmarshaler_from_stream Using standard unmarshaling 0009:trace:ole:StdMarshalImpl_UnmarshalInterface (...,{00000001-0000-0000-c000-000000000046},....) 0009:trace:ole:CoGetPSClsid () riid={00000001-0000-0000-c000-000000000046}, pclsid=0x406ef0d8 0009:trace:ole:WINE_StringFromCLSID 0x409a51b4->{00000001-0000-0000-C000-000000000046} 0009:trace:ole:__CLSIDFromStringA {00000320-0000-0000-C000-000000000046} -> 0x406ef0d8 0009:trace:ole:CoGetPSClsid () Returning CLSID={00000320-0000-0000-c000-000000000046} 0009:trace:ole:WINE_StringFromCLSID 0x406ef0d8->{00000320-0000-0000-C000-000000000046} 0009:trace:ole:CoGetClassObject CLSID: {00000320-0000-0000-c000-000000000046}, IID: {d5f569d0-593b-101a-b569-08002b2dbf7a} 0009:trace:ole:COMPOBJ_DLLList_Add 0014:trace:ole:_LocalServerThread done marshalling IClassFactory 0009:fixme:ole:PIPE_GetNewPipeBuf Could not open named pipe \.\pipe\WINE_OLE_StubMgr_0000001000000014, le is 2 0009:err:ole:StdMarshalImpl_UnmarshalInterface Failed to get an rpc channel buffer for {00000001-0000-0000-c000-000000000046} 0009:err:ole:CoUnmarshalInterface IMarshal::UnmarshalInterface failed, 0x80004005 0009:fixme:ole:CoCreateInstance no classfactory created for CLSID {b6b35894-dd6f-11d3-84ac-00c04f0e1b46}, hres is 0x80004005
On Sat, 2004-12-18 at 07:46 -0800, Bill Medland wrote:
0013:trace:ole:listener_thread Process listener thread starting on (\.\pipe\WINE_OLE_StubMgr_0000001000000011)
...
0009:fixme:ole:PIPE_GetNewPipeBuf Could not open named pipe \.\pipe\WINE_OLE_StubMgr_0000001000000014, le is 2
Well, now we have a variation on the same problem. The apartments are getting mixed up, I suspect because Robs patch creates a new apartment but we still don't create a new listener thread for each apt (rather it's still half process-scoped).
We need to make the listener_thread properly apartment-scoped.
What does the trace+backtrace of the crash with my patch look like?
On December 18, 2004 08:10 am, Mike Hearn wrote:
On Sat, 2004-12-18 at 07:46 -0800, Bill Medland wrote:
0013:trace:ole:listener_thread Process listener thread starting on (\.\pipe\WINE_OLE_StubMgr_0000001000000011)
...
0009:fixme:ole:PIPE_GetNewPipeBuf Could not open named pipe \.\pipe\WINE_OLE_StubMgr_0000001000000014, le is 2
Well, now we have a variation on the same problem. The apartments are getting mixed up, I suspect because Robs patch creates a new apartment but we still don't create a new listener thread for each apt (rather it's still half process-scoped).
We need to make the listener_thread properly apartment-scoped.
What does the trace+backtrace of the crash with my patch look like?
0009:trace:ole:WINE_StringFromCLSID 0x456ed8->{B6B35894-DD6F-11D3-84AC-00C04F0E1B46} 0009:trace:ole:CoGetClassObject CLSID: {b6b35894-dd6f-11d3-84ac-00c04f0e1b46}, IID: {00000001-0000-0000-c000-000000000046} 0009:warn:ole:CoGetClassObject class {B6B35894-DD6F-11D3-84AC-00C04F0E1B46} not registered inproc 0009:trace:ole:create_marshalled_proxy rclsid={b6b35894-dd6f-11d3-84ac-00c04f0e1b46}, iid={00000001-0000-0000-c000-000000000046} 0009:trace:ole:WINE_StringFromCLSID 0x456ed8->{B6B35894-DD6F-11D3-84AC-00C04F0E1B46} 0009:trace:ole:WINE_StringFromCLSID 0x456ed8->{B6B35894-DD6F-11D3-84AC-00C04F0E1B46} 0009:trace:ole:create_server activating local server 'L"G:\runtime\a4wsignonmgr.exe -Embedding"' for {B6B35894-DD6F-11D3-84AC-00C04F0E1B46} 0014:trace:ole:DllMain 0x409e0000 0x1 0x1 0009:warn:ole:create_marshalled_proxy Could not open named pipe to broker \.\pipe{B6B35894-DD6F-11D3-84AC-00C04F0E1B46}, le is 2 0014:trace:ole:DllMain (0x40ab0000,1,0x1) 0014:trace:ole:CoInitializeEx ((nil), 2) 0014:trace:ole:CoInitializeEx () - Initializing the COM libraries 0014:trace:ole:RunningObjectTableImpl_Initialize () 0014:trace:ole:WINE_StringFromCLSID 0x41f320->{A2086A6A-3F3E-457C-8102-A4F99AD7C2DA} 0014:trace:ole:CoRegisterClassObject ({b6b35894-dd6f-11d3-84ac-00c04f0e1b46},0x42130140,0x00000004,0x00000001,0x41f094) 0016:trace:ole:listener_thread Process listener thread starting on (\.\pipe\WINE_OLE_StubMgr_0000001300000014) 0009:warn:ole:create_marshalled_proxy Could not open named pipe to broker \.\pipe{B6B35894-DD6F-11D3-84AC-00C04F0E1B46}, le is 2 0009:warn:ole:create_marshalled_proxy Could not open named pipe to broker \.\pipe{B6B35894-DD6F-11D3-84AC-00C04F0E1B46}, le is 2 0017:trace:ole:_LocalServerThread Starting threader for {b6b35894-dd6f-11d3-84ac-00c04f0e1b46}. 0017:trace:ole:WINE_StringFromCLSID 0x40246150->{B6B35894-DD6F-11D3-84AC-00C04F0E1B46} 0017:trace:ole:_LocalServerThread marshalling IClassFactory to client 0017:trace:ole:CoMarshalInterface (0x402372b8, {00000001-0000-0000-c000-000000000046}, 0x42130140, 0, (nil), 0) 0017:trace:ole:CoGetStandardMarshal ({00000001-0000-0000-c000-000000000046},0x42130140,0,(nil),0,0x42641fd0) 0017:trace:ole:CoMarshalInterface Using standard marshaling 0017:trace:ole:CoMarshalInterface Calling IMarshal::MarshalInterace 0017:trace:ole:StdMarshalImpl_MarshalInterface (...,{00000001-0000-0000-c000-000000000046},...) 0017:trace:ole:CoGetPSClsid () riid={00000001-0000-0000-c000-000000000046}, pclsid=0x42641f64 0017:trace:ole:WINE_StringFromCLSID 0x40a22274->{00000001-0000-0000-C000-000000000046} 0017:trace:ole:__CLSIDFromStringA {00000320-0000-0000-C000-000000000046} -> 0x42641f64 0017:trace:ole:CoGetPSClsid () Returning CLSID={00000320-0000-0000-c000-000000000046} 0017:trace:ole:WINE_StringFromCLSID 0x42641f64->{00000320-0000-0000-C000-000000000046} 0017:trace:ole:CoGetClassObject CLSID: {00000320-0000-0000-c000-000000000046}, IID: {d5f569d0-593b-101a-b569-08002b2dbf7a} 0017:trace:ole:COMPOBJ_DLLList_Add 0017:trace:ole:PSFacBuf_CreateStub ({00000001-0000-0000-c000-000000000046},0x42130140,0x42641f50) 0009:trace:ole:CoUnmarshalInterface (0x40246d60, {00000001-0000-0000-c000-000000000046}, 0x406ef5dc) 0009:trace:ole:get_unmarshaler_from_stream Using standard unmarshaling 0009:trace:ole:StdMarshalImpl_UnmarshalInterface (...,{00000001-0000-0000-c000-000000000046},....) 0009:trace:ole:CoGetPSClsid () riid={00000001-0000-0000-c000-000000000046}, pclsid=0x406ef0d8 0009:trace:ole:WINE_StringFromCLSID 0x409a5274->{00000001-0000-0000-C000-000000000046} 0017:trace:ole:_LocalServerThread done marshalling IClassFactory 0009:trace:ole:__CLSIDFromStringA {00000320-0000-0000-C000-000000000046} -> 0x406ef0d8 0009:trace:ole:CoGetPSClsid () Returning CLSID={00000320-0000-0000-c000-000000000046} 0009:trace:ole:WINE_StringFromCLSID 0x406ef0d8->{00000320-0000-0000-C000-000000000046} 0009:trace:ole:CoGetClassObject CLSID: {00000320-0000-0000-c000-000000000046}, IID: {d5f569d0-593b-101a-b569-08002b2dbf7a} 0009:trace:ole:COMPOBJ_DLLList_Add 0009:trace:ole:CFProxy_CreateInstance ((nil),{00000000-0000-0000-c000-000000000046},0x406ef60c) 0009:trace:ole:PipeBuf_GetBuffer (0x406ef588,{00000001-0000-0000-c000-000000000046}) 0009:trace:ole:PipeBuf_SendReceive () 0018:trace:ole:_StubReaderThread STUB reader thread 13 0018:trace:ole:CFStub_Invoke ->CreateInstance({00000000-0000-0000-c000-000000000046}) 0018:trace:ole:CoMarshalInterface (0x40278858, {00000000-0000-0000-c000-000000000046}, 0x42130124, 0, (nil), 0) 0018:trace:ole:CoGetStandardMarshal ({00000000-0000-0000-c000-000000000046},0x42130124,0,(nil),0,0x42743024) 0018:trace:ole:CoMarshalInterface Using standard marshaling 0018:trace:ole:CoMarshalInterface Calling IMarshal::MarshalInterace 0018:trace:ole:StdMarshalImpl_MarshalInterface (...,{00000000-0000-0000-c000-000000000046},...) wine: Unhandled exception (thread 0018), starting debugger... Backtrace: =>1 0x40901a13 StdMarshalImpl_MarshalInterface+0xa3(iface=0x40247148, pStm=0x40247100, riid=0x42a84138, pv=0x42480180, dwDestContext=0x0, pvDestContext=0x0, mshlflags=0x0) [/home/cvswine/wine/dlls/ole32/compobj_private.h:180] in ole32 (0x42a83ff4) 2 0x40902b07 CoMarshalInterface+0x227(pStream=0x40247100, riid=0x42a84138, pUnk=0x42480180, dwDestContext=0x0, pvDestContext=0x0, mshlFlags=0x0) [/home/cvswine/wine/dlls/ole32/marshal.c:719] in ole32 (0x42a840a4) 3 0x40908cff CFStub_Invoke+0x2e3(iface=0x40246fe8, msg=0x42a84170, chanbuf=0x0) [/home/cvswine/wine/dlls/ole32/oleproxy.c:178] in ole32 (0x42a84154) 4 0x4090acf2 COM_InvokeAndRpcSend+0x92(req=0x40247088) [/home/cvswine/wine/dlls/ole32/rpc.c:346] in ole32 (0x42a841ac) 5 0x4090bc9f _StubReaderThread+0xab(param=0x40246e90) [/home/cvswine/wine/dlls/ole32/rpc.c:745] in ole32 (0x42a841c4) 6 0x40396593 THREAD_Start+0xef(ptr=0x40246f70) [/home/cvswine/wine/dlls/kernel/thread.c:107] in kernel32 (0x42a84298) 7 0x400c314f start_thread+0x14b(info=0x40246f90) [/home/cvswine/wine/dlls/ntdll/thread.c:201] in ntdll (0x42a84ad4) 8 0x40044941 ?? +0x1b1 in libpthread.so.0 (0x42a84bd4) 9 0x420da1ca ?? +0x3a in libc.so.6 (0x00000000) Wine-dbg>
On Sat, 18 Dec 2004 08:45:46 -0800, Bill Medland wrote:
0018:trace:ole:CoMarshalInterface Using standard marshaling 0018:trace:ole:CoMarshalInterface Calling IMarshal::MarshalInterace 0018:trace:ole:StdMarshalImpl_MarshalInterface (...,{00000000-0000-0000-c000-000000000046},...) wine: Unhandled exception (thread 0018), starting debugger... Backtrace: =>1 0x40901a13 StdMarshalImpl_MarshalInterface+0xa3(iface=0x40247148, pStm=0x40247100, riid=0x42a84138, pv=0x42480180, dwDestContext=0x0, pvDestContext=0x0, mshlflags=0x0) [/home/cvswine/wine/dlls/ole32/compobj_private.h:180] in ole32 (0x42a83ff4) 2 0x40902b07 CoMarshalInterface+0x227(pStream=0x40247100, riid=0x42a84138, pUnk=0x42480180, dwDestContext=0x0, pvDestContext=0x0, mshlFlags=0x0) [/home/cvswine/wine/dlls/ole32/marshal.c:719] in ole32 (0x42a840a4) 3 0x40908cff CFStub_Invoke+0x2e3(iface=0x40246fe8, msg=0x42a84170, chanbuf=0x0) [/home/cvswine/wine/dlls/ole32/oleproxy.c:178] in ole32 (0x42a84154) 4 0x4090acf2 COM_InvokeAndRpcSend+0x92(req=0x40247088) [/home/cvswine/wine/dlls/ole32/rpc.c:346] in ole32 (0x42a841ac) 5 0x4090bc9f _StubReaderThread+0xab(param=0x40246e90) [/home/cvswine/wine/dlls/ole32/rpc.c:745] in ole32 (0x42a841c4) 6 0x40396593 THREAD_Start+0xef(ptr=0x40246f70) [/home/cvswine/wine/dlls/kernel/thread.c:107] in kernel32 (0x42a84298)
OK, the problem here is that the StubReaderThread is *also* not in an apartment. With my patch it does seem to be getting further though than with the CoInitializeEx patch, it does actually connect and do an IClassFactory::CreateInstance.
As a hack you can whack a CoInitializeEx at the start of _StubReaderThread but it's wrong and will probably not work either.
I think we actually need to migrate the apt through the pipe registration code so when PIPE_RegisterPipe starts the new thread, it can also join the apartment which did the original registration. This is continuing the idea of making all the implementation threads use the same apartment.
I'll talk with Rob about this, as we have some DCOM work still in mid-air.
thanks -mike
Mike Hearn wrote:
On Sat, 2004-12-18 at 07:46 -0800, Bill Medland wrote:
0013:trace:ole:listener_thread Process listener thread starting on (\.\pipe\WINE_OLE_StubMgr_0000001000000011)
...
0009:fixme:ole:PIPE_GetNewPipeBuf Could not open named pipe \.\pipe\WINE_OLE_StubMgr_0000001000000014, le is 2
Well, now we have a variation on the same problem. The apartments are getting mixed up, I suspect because Robs patch creates a new apartment but we still don't create a new listener thread for each apt (rather it's still half process-scoped).
Yes, Mike, you are correct. It is not half process-scoped, but instead now scoped with the wrong apartment.
We need to make the listener_thread properly apartment-scoped.
Yes. Bill, you can either wait for my patch to fix local servers, or you can revert to ole32 as of 28th November.
Rob
On Sat, 18 Dec 2004 07:46:42 -0800, Bill Medland wrote:
If I combine it with Rob's CoInitializeEx patch rather than Mike's then it executes but still fails, as follows:
Try this patch. It's a modified form of Robs:
Index: dlls/ole32/rpc.c =================================================================== RCS file: /home/wine/wine/dlls/ole32/rpc.c,v retrieving revision 1.31 diff -u -p -d -r1.31 rpc.c --- dlls/ole32/rpc.c 14 Dec 2004 15:28:58 -0000 1.31 +++ dlls/ole32/rpc.c 18 Dec 2004 16:59:43 -0000 @@ -758,9 +758,10 @@ static DWORD WINAPI listener_thread(LPVO { char pipefn[200]; HANDLE listenPipe; + APARTMENT *apt = (APARTMENT *) param;
- sprintf(pipefn,OLESTUBMGR"_%08lx",GetCurrentProcessId()); - TRACE("Process listener thread starting on (%s)\n",pipefn); + sprintf(pipefn,OLESTUBMGR"_%08lx%08lx", apt->oxid >> 32, apt->oxid); + TRACE("Apartment listener thread starting on (%s)\n",pipefn);
while (1) { listenPipe = CreateNamedPipeA( @@ -789,13 +790,10 @@ static DWORD WINAPI listener_thread(LPVO
void start_listener_thread() { - static BOOL running = FALSE; - DWORD tid; - - if (!running) - { - running = TRUE; - CreateThread(NULL, 0, listener_thread, NULL, 0, &tid); - Sleep(2000); /* actually we just try opening the pipe until it succeeds */ - } + APARTMENT *apt = COM_CurrentApt(); + + if (!apt->tid) + { + CreateThread(NULL, 0, listener_thread, apt, 0, &apt->tid); + } }
Mike Hearn wrote:
On Fri, 17 Dec 2004 10:49:45 -0800, Bill Medland wrote:
Does anyone know anything about this? e.g. when starting a new thread where does the apartment get initialized?
It's supposed to get initialized in the call to CoInitialize[Ex] however the _LocalServerThread never calls this as it's an internal implementation detail of out of process DCOM.
This looks like we haven't got the design quite right here, the LocalServerThread doesn't exist in native DCOM as far as I can tell so it may need to be replaced by something else.
Rewriting this stuff is next on my todo list. The correct fix is to marshal it in the context of the calling thread, rather than in the new thread. This part is implemented in the native version as kind of a mix between the rpcrt4 thread pooling and undocumented local activator interfaces registered for each apartment.
The code in StdMarshalImpl is correct, the problem is that the local server thread is violating the COM laws by using CoMarshalInterface before entering an apartment.
For now, does this patch help?
Index: dlls/ole32/compobj.c
RCS file: /home/wine/wine/dlls/ole32/compobj.c,v retrieving revision 1.113 diff -u -p -r1.113 compobj.c --- dlls/ole32/compobj.c 14 Dec 2004 15:28:58 -0000 1.113 +++ dlls/ole32/compobj.c 17 Dec 2004 19:13:22 -0000 @@ -102,6 +102,7 @@ typedef struct tagRegisteredClass DWORD connectFlags; DWORD dwCookie; HANDLE hThread; /* only for localserver */
- APARTMENT *apt; /* owning apartment */ struct tagRegisteredClass* nextClass;
} RegisteredClass;
@@ -1107,6 +1108,13 @@ _LocalServerThread(LPVOID param) {
TRACE("Starting threader for %s.\n",debugstr_guid(&newClass->classIdentifier));
- /* we need to enter the apartment of the thread which registered
* the class object to perform the next stage
*/
- assert( newClass->apt );
- NtCurrentTeb()->ReservedForOle = newClass->apt;
- strcpy(pipefn,PIPEPREF); WINE_StringFromCLSID(&newClass->classIdentifier,pipefn+strlen(PIPEPREF));
@@ -1219,6 +1227,12 @@ HRESULT WINAPI CoRegisterClassObject( if ( (lpdwRegister==0) || (pUnk==0) ) return E_INVALIDARG;
if (!COM_CurrentApt())
{
ERR("COM was not initialized\n");
return CO_E_NOTINITIALIZED;
}
*lpdwRegister = 0;
/*
@@ -1240,6 +1254,7 @@ HRESULT WINAPI CoRegisterClassObject( newClass->classIdentifier = *rclsid; newClass->runContext = dwClsContext; newClass->connectFlags = flags;
- newClass->apt = COM_CurrentApt(); /*
- Use the address of the chain node as the cookie since we are sure it's
- unique.
That patch is very hackish and needlessly complicated. This patch accomplishes the same task in fewer lines (note that this is not the best solution for the problem, I am working on that):
Index: compobj.c =================================================================== RCS file: /home/wine/wine/dlls/ole32/compobj.c,v retrieving revision 1.113 diff -u -p -r1.113 compobj.c --- compobj.c 14 Dec 2004 15:28:58 -0000 1.113 +++ compobj.c 18 Dec 2004 13:58:03 -0000 @@ -1107,6 +1107,8 @@ _LocalServerThread(LPVOID param) {
TRACE("Starting threader for %s.\n",debugstr_guid(&newClass->classIdentifier));
+ CoInitializeEx(NULL, COINIT_APARTMENTTHREADED); + strcpy(pipefn,PIPEPREF);
WINE_StringFromCLSID(&newClass->classIdentifier,pipefn+strlen(PIPEPREF));
Rob
On Sat, 2004-12-18 at 13:13 +0000, Robert Shearman wrote:
That patch is very hackish and needlessly complicated. This patch accomplishes the same task in fewer lines (note that this is not the best solution for the problem, I am working on that):
Index: compobj.c
RCS file: /home/wine/wine/dlls/ole32/compobj.c,v retrieving revision 1.113 diff -u -p -r1.113 compobj.c --- compobj.c 14 Dec 2004 15:28:58 -0000 1.113 +++ compobj.c 18 Dec 2004 13:58:03 -0000 @@ -1107,6 +1107,8 @@ _LocalServerThread(LPVOID param) {
TRACE("Starting threader for
%s.\n",debugstr_guid(&newClass->classIdentifier));
- CoInitializeEx(NULL, COINIT_APARTMENTTHREADED);
- strcpy(pipefn,PIPEPREF);
WINE_StringFromCLSID(&newClass->classIdentifier,pipefn+strlen (PIPEPREF));
That doesn't look right, it'll create a new apartment instead of using the one that the program itself created. I don't think we should be creating new apartments that don't correspond to anything the app did, Win32 generally expects the API user to do it manually. It'll make the code more confusing, especially once thread affinity is implemented.