source: trunk/src/ole32/rpc.c@ 7926

Last change on this file since 7926 was 7926, checked in by sandervl, 24 years ago

Wine 20020215 resync

File size: 17.3 KB
Line 
1/*
2 * (Local) RPC Stuff
3 *
4 * Copyright 2002 Marcus Meissner
5 */
6
7#include "config.h"
8
9#include <stdlib.h>
10#include <stdio.h>
11#include <string.h>
12#include <assert.h>
13
14#include "windef.h"
15#include "objbase.h"
16#include "ole2.h"
17#include "ole2ver.h"
18#include "rpc.h"
19#include "winerror.h"
20#include "winreg.h"
21#include "wownt32.h"
22#include "wtypes.h"
23#include "wine/unicode.h"
24#include "wine/obj_base.h"
25#include "wine/obj_clientserver.h"
26#include "wine/obj_misc.h"
27#include "wine/obj_marshal.h"
28#include "wine/obj_storage.h"
29#include "wine/obj_channel.h"
30#include "wine/winbase16.h"
31#include "compobj_private.h"
32#include "ifs.h"
33
34#include "compobj_private.h"
35
36#include "debugtools.h"
37
38DEFAULT_DEBUG_CHANNEL(ole);
39
40typedef struct _wine_rpc_request {
41 int state;
42 HANDLE hPipe; /* temp copy of handle */
43 wine_rpc_request_header reqh;
44 wine_rpc_response_header resph;
45 LPBYTE Buffer;
46} wine_rpc_request;
47
48static wine_rpc_request **reqs = NULL;
49static int nrofreqs = 0;
50
51/* This pipe is _thread_ based */
52typedef struct _wine_pipe {
53 wine_marshal_id mid; /* target mid */
54 DWORD tid; /* thread in which we execute */
55 HANDLE hPipe;
56
57 int pending;
58 HANDLE hThread;
59 CRITICAL_SECTION crit;
60} wine_pipe;
61
62static wine_pipe *pipes = NULL;
63static int nrofpipes = 0;
64
65typedef struct _PipeBuf {
66 ICOM_VTABLE(IRpcChannelBuffer) *lpVtbl;
67 DWORD ref;
68
69 wine_marshal_id mid;
70 wine_pipe *pipe;
71} PipeBuf;
72
73static int nrofreaders = 0;
74
75static HRESULT WINAPI
76_xread(HANDLE hf, LPVOID ptr, DWORD size) {
77 DWORD res;
78 if (!ReadFile(hf,ptr,size,&res,NULL)) {
79 FIXME("Failed to read from %x, le is %lx\n",hf,GetLastError());
80 return E_FAIL;
81 }
82 if (res!=size) {
83 FIXME("Read only %ld of %ld bytes.\n",res,size);
84 return E_FAIL;
85 }
86 return S_OK;
87}
88
89static void
90drs(LPCSTR where) {
91 int i, states[10];
92
93 return ;
94
95 memset(states,0,sizeof(states));
96 for (i=nrofreqs;i--;)
97 states[reqs[i]->state]++;
98 FIXME("%lx/%s/%d: rq %d, w %d, rg %d, rsq %d, rsg %d, d %d\n",
99 GetCurrentProcessId(),
100 where,
101 nrofreaders,
102 states[REQSTATE_REQ_QUEUED],
103 states[REQSTATE_REQ_WAITING_FOR_REPLY],
104 states[REQSTATE_REQ_GOT],
105 states[REQSTATE_RESP_QUEUED],
106 states[REQSTATE_RESP_GOT],
107 states[REQSTATE_DONE]
108 );
109}
110
111static HRESULT WINAPI
112_xwrite(HANDLE hf, LPVOID ptr, DWORD size) {
113 DWORD res;
114 if (!WriteFile(hf,ptr,size,&res,NULL)) {
115 FIXME("Failed to write to %x, le is %lx\n",hf,GetLastError());
116 return E_FAIL;
117 }
118 if (res!=size) {
119 FIXME("Wrote only %ld of %ld bytes.\n",res,size);
120 return E_FAIL;
121 }
122 return S_OK;
123}
124
125static DWORD WINAPI _StubReaderThread(LPVOID);
126
127static HRESULT
128PIPE_RegisterPipe(wine_marshal_id *mid, HANDLE hPipe, BOOL startreader) {
129 int i;
130 char pipefn[100];
131
132 for (i=0;i<nrofpipes;i++)
133 if (pipes[i].mid.processid==mid->processid)
134 return S_OK;
135 if (pipes)
136 pipes=(wine_pipe*)HeapReAlloc(GetProcessHeap(),0,pipes,sizeof(pipes[0])*(nrofpipes+1));
137 else
138 pipes=(wine_pipe*)HeapAlloc(GetProcessHeap(),0,sizeof(pipes[0]));
139 if (!pipes) return E_OUTOFMEMORY;
140 sprintf(pipefn,OLESTUBMGR"_%08lx",mid->processid);
141 memcpy(&(pipes[nrofpipes].mid),mid,sizeof(*mid));
142 pipes[nrofpipes].hPipe = hPipe;
143 InitializeCriticalSection(&(pipes[nrofpipes].crit));
144 nrofpipes++;
145 if (startreader) {
146#ifdef __WIN32OS2__
147 pipes[nrofpipes-1].hThread = CreateThread(NULL,0,_StubReaderThread,(LPVOID)(pipes+(nrofpipes-1)),0,&(pipes[nrofpipes-1].tid));
148#else
149 pipes[nrofpipes-1].hThread = CreateThread(NULL,0,_StubReaderThread,(LPVOID)pipes+(nrofpipes-1),0,&(pipes[nrofpipes-1].tid));
150#endif
151 } else {
152 pipes[nrofpipes-1].tid = GetCurrentThreadId();
153 }
154 return S_OK;
155}
156
157static HANDLE
158PIPE_FindByMID(wine_marshal_id *mid) {
159 int i;
160 for (i=0;i<nrofpipes;i++)
161 if ((pipes[i].mid.processid==mid->processid) &&
162 (GetCurrentThreadId()==pipes[i].tid)
163 )
164 return pipes[i].hPipe;
165 return INVALID_HANDLE_VALUE;
166}
167
168static wine_pipe*
169PIPE_GetFromMID(wine_marshal_id *mid) {
170 int i;
171 for (i=0;i<nrofpipes;i++) {
172 if ((pipes[i].mid.processid==mid->processid) &&
173 (GetCurrentThreadId()==pipes[i].tid)
174 )
175 return pipes+i;
176 }
177 return NULL;
178}
179
180static HRESULT
181RPC_GetRequest(wine_rpc_request **req) {
182 static int reqid = 0xdeadbeef;
183 int i;
184
185 for (i=0;i<nrofreqs;i++) { /* try to reuse */
186 if (reqs[i]->state == REQSTATE_DONE) {
187 reqs[i]->reqh.reqid = reqid++;
188 reqs[i]->resph.reqid = reqs[i]->reqh.reqid;
189 reqs[i]->hPipe = INVALID_HANDLE_VALUE;
190 *req = reqs[i];
191 reqs[i]->state = REQSTATE_START;
192 return S_OK;
193 }
194 }
195 /* create new */
196 if (reqs)
197 reqs = (wine_rpc_request**)HeapReAlloc(
198 GetProcessHeap(),
199 HEAP_ZERO_MEMORY,
200 reqs,
201 sizeof(wine_rpc_request*)*(nrofreqs+1)
202 );
203 else
204 reqs = (wine_rpc_request**)HeapAlloc(
205 GetProcessHeap(),
206 HEAP_ZERO_MEMORY,
207 sizeof(wine_rpc_request*)
208 );
209 if (!reqs)
210 return E_OUTOFMEMORY;
211 reqs[nrofreqs] = (wine_rpc_request*)HeapAlloc(GetProcessHeap(),HEAP_ZERO_MEMORY,sizeof(wine_rpc_request));
212 reqs[nrofreqs]->reqh.reqid = reqid++;
213 reqs[nrofreqs]->resph.reqid = reqs[nrofreqs]->reqh.reqid;
214 reqs[nrofreqs]->hPipe = INVALID_HANDLE_VALUE;
215 *req = reqs[nrofreqs];
216 reqs[nrofreqs]->state = REQSTATE_START;
217 nrofreqs++;
218 return S_OK;
219}
220
221static void
222RPC_FreeRequest(wine_rpc_request *req) {
223 req->state = REQSTATE_DONE; /* Just reuse slot. */
224 return;
225}
226
227static HRESULT WINAPI
228PipeBuf_QueryInterface(
229 LPRPCCHANNELBUFFER iface,REFIID riid,LPVOID *ppv
230) {
231 *ppv = NULL;
232 if (IsEqualIID(riid,&IID_IRpcChannelBuffer) || IsEqualIID(riid,&IID_IUnknown)) {
233 *ppv = (LPVOID)iface;
234 IUnknown_AddRef(iface);
235 return S_OK;
236 }
237 return E_NOINTERFACE;
238}
239
240static ULONG WINAPI
241PipeBuf_AddRef(LPRPCCHANNELBUFFER iface) {
242 ICOM_THIS(PipeBuf,iface);
243 This->ref++;
244 return This->ref;
245}
246
247static ULONG WINAPI
248PipeBuf_Release(LPRPCCHANNELBUFFER iface) {
249 ICOM_THIS(PipeBuf,iface);
250 This->ref--;
251 if (This->ref)
252 return This->ref;
253 ERR("Free all stuff.\n");
254 HeapFree(GetProcessHeap(),0,This);
255 return 0;
256}
257
258static HRESULT WINAPI
259PipeBuf_GetBuffer(
260 LPRPCCHANNELBUFFER iface,RPCOLEMESSAGE* msg,REFIID riid
261) {
262 /*ICOM_THIS(PipeBuf,iface);*/
263
264 TRACE("(%p,%s), slightly wrong.\n",msg,debugstr_guid(riid));
265 /* probably reuses IID in real. */
266 if (msg->cbBuffer && (msg->Buffer == NULL))
267 msg->Buffer = HeapAlloc(GetProcessHeap(),0,msg->cbBuffer);
268 return S_OK;
269}
270
271static HRESULT
272_invoke_onereq(wine_rpc_request *req) {
273 IRpcStubBuffer *stub;
274 RPCOLEMESSAGE msg;
275 HRESULT hres;
276 DWORD reqtype;
277
278 hres = MARSHAL_Find_Stub_Buffer(&(req->reqh.mid),&stub);
279 if (hres) {
280 ERR("Stub not found?\n");
281 return hres;
282 }
283 msg.Buffer = req->Buffer;
284 msg.iMethod = req->reqh.iMethod;
285 msg.cbBuffer = req->reqh.cbBuffer;
286 req->state = REQSTATE_INVOKING;
287 req->resph.retval = IRpcStubBuffer_Invoke(stub,&msg,NULL);
288 req->Buffer = msg.Buffer;
289 req->resph.cbBuffer = msg.cbBuffer;
290 reqtype = REQTYPE_RESPONSE;
291 hres = _xwrite(req->hPipe,&reqtype,sizeof(reqtype));
292 if (hres) return hres;
293 hres = _xwrite(req->hPipe,&(req->resph),sizeof(req->resph));
294 if (hres) return hres;
295 hres = _xwrite(req->hPipe,req->Buffer,req->resph.cbBuffer);
296 if (hres) return hres;
297 req->state = REQSTATE_DONE;
298 drs("invoke");
299 return S_OK;
300}
301
302static HRESULT _read_one(wine_pipe *xpipe);
303
304static HRESULT
305RPC_QueueRequestAndWait(wine_rpc_request *req) {
306 int i;
307 wine_rpc_request *xreq;
308 HRESULT hres;
309 DWORD reqtype;
310 wine_pipe *xpipe = PIPE_GetFromMID(&(req->reqh.mid));
311
312 if (!xpipe) {
313 FIXME("no pipe found.\n");
314 return E_POINTER;
315 }
316 if (GetCurrentProcessId() == req->reqh.mid.processid) {
317 ERR("In current process?\n");
318 return E_FAIL;
319 }
320 req->hPipe = xpipe->hPipe;
321 req->state = REQSTATE_REQ_WAITING_FOR_REPLY;
322 reqtype = REQTYPE_REQUEST;
323 hres = _xwrite(req->hPipe,&reqtype,sizeof(reqtype));
324 if (hres) return hres;
325 hres = _xwrite(req->hPipe,&(req->reqh),sizeof(req->reqh));
326 if (hres) return hres;
327 hres = _xwrite(req->hPipe,req->Buffer,req->reqh.cbBuffer);
328 if (hres) return hres;
329
330 while (1) {
331 /*WaitForSingleObject(hRpcChanged,INFINITE);*/
332 hres = _read_one(xpipe);
333 if (hres) break;
334
335 for (i=0;i<nrofreqs;i++) {
336 xreq = reqs[i];
337 if ((xreq->state==REQSTATE_REQ_GOT) && (xreq->hPipe==req->hPipe)) {
338 _invoke_onereq(xreq);
339 }
340 }
341 if (req->state == REQSTATE_RESP_GOT)
342 return S_OK;
343 }
344 return hres;
345}
346
347static HRESULT WINAPI
348PipeBuf_SendReceive(
349 LPRPCCHANNELBUFFER iface,RPCOLEMESSAGE* msg,ULONG *status
350) {
351 ICOM_THIS(PipeBuf,iface);
352 wine_rpc_request *req;
353 HRESULT hres;
354
355 TRACE("()\n");
356
357 if (This->mid.processid == GetCurrentProcessId()) {
358 ERR("Need to call directly!\n");
359 return E_FAIL;
360 }
361
362 hres = RPC_GetRequest(&req);
363 if (hres) return hres;
364 req->reqh.iMethod = msg->iMethod;
365 req->reqh.cbBuffer = msg->cbBuffer;
366 memcpy(&(req->reqh.mid),&(This->mid),sizeof(This->mid));
367 req->Buffer = msg->Buffer;
368 hres = RPC_QueueRequestAndWait(req);
369 if (hres) {
370 RPC_FreeRequest(req);
371 return hres;
372 }
373 msg->cbBuffer = req->resph.cbBuffer;
374 msg->Buffer = req->Buffer;
375 *status = req->resph.retval;
376 RPC_FreeRequest(req);
377 return S_OK;
378}
379
380
381static HRESULT WINAPI
382PipeBuf_FreeBuffer(LPRPCCHANNELBUFFER iface,RPCOLEMESSAGE* msg) {
383 FIXME("(%p), stub!\n",msg);
384 return E_FAIL;
385}
386
387static HRESULT WINAPI
388PipeBuf_GetDestCtx(
389 LPRPCCHANNELBUFFER iface,DWORD* pdwDestContext,void** ppvDestContext
390) {
391 FIXME("(%p,%p), stub!\n",pdwDestContext,ppvDestContext);
392 return E_FAIL;
393}
394
395static HRESULT WINAPI
396PipeBuf_IsConnected(LPRPCCHANNELBUFFER iface) {
397 FIXME("(), stub!\n");
398 return S_OK;
399}
400
401static ICOM_VTABLE(IRpcChannelBuffer) pipebufvt = {
402 ICOM_MSVTABLE_COMPAT_DummyRTTIVALUE
403 PipeBuf_QueryInterface,
404 PipeBuf_AddRef,
405 PipeBuf_Release,
406 PipeBuf_GetBuffer,
407 PipeBuf_SendReceive,
408 PipeBuf_FreeBuffer,
409 PipeBuf_GetDestCtx,
410 PipeBuf_IsConnected
411};
412
413HRESULT
414PIPE_GetNewPipeBuf(wine_marshal_id *mid, IRpcChannelBuffer **pipebuf) {
415 wine_marshal_id ourid;
416 DWORD res;
417 HANDLE hPipe;
418 HRESULT hres;
419 PipeBuf *pbuf;
420
421 hPipe = PIPE_FindByMID(mid);
422 if (hPipe == INVALID_HANDLE_VALUE) {
423 char pipefn[200];
424 sprintf(pipefn,OLESTUBMGR"_%08lx",mid->processid);
425 hPipe = CreateFileA(
426 pipefn,
427 GENERIC_READ|GENERIC_WRITE,
428 0,
429 NULL,
430 OPEN_EXISTING,
431 0,
432 -1
433 );
434 if (hPipe == INVALID_HANDLE_VALUE) {
435 FIXME("Could not open named pipe %s, le is %lx\n",pipefn,GetLastError());
436 return E_FAIL;
437 }
438 hres = PIPE_RegisterPipe(mid, hPipe, FALSE);
439 if (hres) return hres;
440 memset(&ourid,0,sizeof(ourid));
441 ourid.processid = GetCurrentProcessId();
442 if (!WriteFile(hPipe,&ourid,sizeof(ourid),&res,NULL)||(res!=sizeof(ourid))) {
443 ERR("Failed writing startup mid!\n");
444 return E_FAIL;
445 }
446 }
447 pbuf = (PipeBuf*)HeapAlloc(GetProcessHeap(),HEAP_ZERO_MEMORY,sizeof(PipeBuf));
448 pbuf->lpVtbl = &pipebufvt;
449 pbuf->ref = 1;
450 memcpy(&(pbuf->mid),mid,sizeof(*mid));
451 *pipebuf = (IRpcChannelBuffer*)pbuf;
452 return S_OK;
453}
454
455static HRESULT
456create_server(REFCLSID rclsid) {
457 HKEY key;
458 char buf[200];
459 HRESULT hres = E_UNEXPECTED;
460 char xclsid[80];
461 WCHAR dllName[MAX_PATH+1];
462 DWORD dllNameLen = sizeof(dllName);
463 STARTUPINFOW sinfo;
464 PROCESS_INFORMATION pinfo;
465
466 WINE_StringFromCLSID((LPCLSID)rclsid,xclsid);
467
468 sprintf(buf,"CLSID\\%s\\LocalServer32",xclsid);
469 hres = RegOpenKeyExA(HKEY_CLASSES_ROOT, buf, 0, KEY_READ, &key);
470
471 if (hres != ERROR_SUCCESS)
472 return REGDB_E_CLASSNOTREG;
473
474 memset(dllName,0,sizeof(dllName));
475 hres= RegQueryValueExW(key,NULL,NULL,NULL,(LPBYTE)dllName,&dllNameLen);
476 if (hres)
477 return REGDB_E_CLASSNOTREG; /* FIXME: check retval */
478 RegCloseKey(key);
479 memset(&sinfo,0,sizeof(sinfo));
480 sinfo.cb = sizeof(sinfo);
481 if (!CreateProcessW(NULL,dllName,NULL,NULL,FALSE,0,NULL,NULL,&sinfo,&pinfo))
482 return E_FAIL;
483 return S_OK;
484}
485/* http://msdn.microsoft.com/library/en-us/dnmsj99/html/com0199.asp, Figure 4 */
486HRESULT create_marshalled_proxy(REFCLSID rclsid, REFIID iid, LPVOID *ppv) {
487 HRESULT hres;
488 HANDLE hPipe;
489 char pipefn[200];
490 DWORD res,bufferlen;
491 char marshalbuffer[200];
492 IStream *pStm;
493 LARGE_INTEGER seekto;
494 ULARGE_INTEGER newpos;
495 int tries = 0;
496#define MAXTRIES 10000
497
498 strcpy(pipefn,PIPEPREF);
499 WINE_StringFromCLSID(rclsid,pipefn+strlen(PIPEPREF));
500
501 while (tries++<MAXTRIES) {
502 hPipe = CreateFileA(
503 pipefn,
504 GENERIC_READ|GENERIC_WRITE,
505 0,
506 NULL,
507 OPEN_EXISTING,
508 0,
509 -1
510 );
511 if (hPipe == INVALID_HANDLE_VALUE) {
512 if (tries == 1) {
513 if ((hres = create_server(rclsid)))
514 return hres;
515 Sleep(1000);
516 } else {
517 WARN("Could not open named pipe to broker %s, le is %lx\n",pipefn,GetLastError());
518 Sleep(1000);
519 }
520 continue;
521 }
522 bufferlen = 0;
523 if (!ReadFile(hPipe,marshalbuffer,sizeof(marshalbuffer),&bufferlen,NULL)) {
524 FIXME("Failed to read marshal id from classfactory of %s.\n",debugstr_guid(rclsid));
525 Sleep(1000);
526 continue;
527 }
528 CloseHandle(hPipe);
529 break;
530 }
531 if (tries>=MAXTRIES)
532 return E_NOINTERFACE;
533 hres = CreateStreamOnHGlobal(0,TRUE,&pStm);
534 if (hres) return hres;
535 hres = IStream_Write(pStm,marshalbuffer,bufferlen,&res);
536 if (hres) goto out;
537 seekto.s.LowPart = 0;seekto.s.HighPart = 0;
538 hres = IStream_Seek(pStm,seekto,SEEK_SET,&newpos);
539 hres = CoUnmarshalInterface(pStm,&IID_IClassFactory,ppv);
540out:
541 IStream_Release(pStm);
542 return hres;
543}
544
545
546static void WINAPI
547PIPE_StartRequestThread(HANDLE xhPipe) {
548 wine_marshal_id remoteid;
549 HRESULT hres;
550
551 hres = _xread(xhPipe,&remoteid,sizeof(remoteid));
552 if (hres) {
553 ERR("Failed to read remote mid!\n");
554 return;
555 }
556 PIPE_RegisterPipe(&remoteid,xhPipe, TRUE);
557}
558
559static HRESULT
560_read_one(wine_pipe *xpipe) {
561 DWORD reqtype;
562 HRESULT hres = S_OK;
563 HANDLE xhPipe = xpipe->hPipe;
564
565 /*FIXME("%lx %d reading reqtype\n",GetCurrentProcessId(),xhPipe);*/
566 hres = _xread(xhPipe,&reqtype,sizeof(reqtype));
567 if (hres) goto end;
568 EnterCriticalSection(&(xpipe->crit));
569 /*FIXME("%lx got reqtype %ld\n",GetCurrentProcessId(),reqtype);*/
570
571 if (reqtype == REQTYPE_REQUEST) {
572 wine_rpc_request *xreq;
573 RPC_GetRequest(&xreq);
574 xreq->hPipe = xhPipe;
575 hres = _xread(xhPipe,&(xreq->reqh),sizeof(xreq->reqh));
576 if (hres) goto end;
577 xreq->resph.reqid = xreq->reqh.reqid;
578 xreq->Buffer = HeapAlloc(GetProcessHeap(),0, xreq->reqh.cbBuffer);
579 hres = _xread(xhPipe,xreq->Buffer,xreq->reqh.cbBuffer);
580 if (hres) goto end;
581 xreq->state = REQSTATE_REQ_GOT;
582 goto end;
583 }
584 if (reqtype == REQTYPE_RESPONSE) {
585 wine_rpc_response_header resph;
586 int i;
587
588 hres = _xread(xhPipe,&resph,sizeof(resph));
589 if (hres) goto end;
590 for (i=nrofreqs;i--;) {
591 wine_rpc_request *xreq = reqs[i];
592 if (xreq->state != REQSTATE_REQ_WAITING_FOR_REPLY)
593 continue;
594 if (xreq->reqh.reqid == resph.reqid) {
595 memcpy(&(xreq->resph),&resph,sizeof(resph));
596 xreq->Buffer = HeapReAlloc(GetProcessHeap(),HEAP_ZERO_MEMORY,xreq->Buffer,xreq->resph.cbBuffer);
597 hres = _xread(xhPipe,xreq->Buffer,xreq->resph.cbBuffer);
598 if (hres) goto end;
599 xreq->state = REQSTATE_RESP_GOT;
600 /*PulseEvent(hRpcChanged);*/
601 goto end;
602 }
603 }
604 ERR("Did not find request for id %lx\n",resph.reqid);
605 hres = S_OK;
606 goto end;
607 }
608 ERR("Unknown reqtype %ld\n",reqtype);
609 hres = E_FAIL;
610end:
611 LeaveCriticalSection(&(xpipe->crit));
612 return hres;
613}
614
615static DWORD WINAPI
616_StubReaderThread(LPVOID param) {
617 wine_pipe *xpipe = (wine_pipe*)param;
618 HANDLE xhPipe = xpipe->hPipe;
619 HRESULT hres;
620
621 TRACE("STUB reader thread %lx\n",GetCurrentProcessId());
622 while (1) {
623 int i;
624 hres = _read_one(xpipe);
625 if (hres) break;
626
627 for (i=nrofreqs;i--;) {
628 wine_rpc_request *xreq = reqs[i];
629 if ((xreq->state == REQSTATE_REQ_GOT) && (xreq->hPipe == xhPipe)) {
630 _invoke_onereq(xreq);
631 }
632 }
633 }
634 FIXME("Failed with hres %lx\n",hres);
635 CloseHandle(xhPipe);
636 return 0;
637}
638
639static DWORD WINAPI
640_StubMgrThread(LPVOID param) {
641 char pipefn[200];
642 HANDLE listenPipe;
643
644 sprintf(pipefn,OLESTUBMGR"_%08lx",GetCurrentProcessId());
645 TRACE("Stub Manager Thread starting on (%s)\n",pipefn);
646
647 listenPipe = CreateNamedPipeA(
648 pipefn,
649 PIPE_ACCESS_DUPLEX,
650 PIPE_TYPE_BYTE|PIPE_WAIT,
651 PIPE_UNLIMITED_INSTANCES,
652 4096,
653 4096,
654 NMPWAIT_USE_DEFAULT_WAIT,
655 NULL
656 );
657 if (listenPipe == INVALID_HANDLE_VALUE) {
658 FIXME("pipe creation failed for %s, le is %lx\n",pipefn,GetLastError());
659 return 1; /* permanent failure, so quit stubmgr thread */
660 }
661
662 while (1) {
663 if (!ConnectNamedPipe(listenPipe,NULL)) {
664 ERR("Failure during ConnectNamedPipe %lx!\n",GetLastError());
665 CloseHandle(listenPipe);
666 continue;
667 }
668 PIPE_StartRequestThread(listenPipe);
669 listenPipe = CreateNamedPipeA(
670 pipefn,
671 PIPE_ACCESS_DUPLEX,
672 PIPE_TYPE_BYTE|PIPE_WAIT,
673 PIPE_UNLIMITED_INSTANCES,
674 4096,
675 4096,
676 NMPWAIT_USE_DEFAULT_WAIT,
677 NULL
678 );
679 if (listenPipe == INVALID_HANDLE_VALUE) {
680 FIXME("pipe creation failed for %s, le is %lx\n",pipefn,GetLastError());
681 return 1; /* permanent failure, so quit stubmgr thread */
682 }
683 }
684 return 0;
685}
686
687void
688STUBMGR_Start() {
689 static BOOL stubMgrRunning = FALSE;
690 DWORD tid;
691
692 if (!stubMgrRunning) {
693 stubMgrRunning = TRUE;
694 CreateThread(NULL,0,_StubMgrThread,NULL,0,&tid);
695 Sleep(2000); /* actually we just try opening the pipe until it succeeds */
696 }
697}
Note: See TracBrowser for help on using the repository browser.