ReactOS 0.4.15-dev-8339-g4028de8
compositemoniker.c
Go to the documentation of this file.
1/*
2 * CompositeMonikers implementation
3 *
4 * Copyright 1999 Noomen Hamza
5 *
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.
10 *
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.
15 *
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
19 */
20
21#include <assert.h>
22#include <stdarg.h>
23#include <string.h>
24
25#define COBJMACROS
26
27#include "windef.h"
28#include "winbase.h"
29#include "winuser.h"
30#include "winerror.h"
31#include "wine/debug.h"
32#include "ole2.h"
33#include "moniker.h"
34
36
37#define BLOCK_TAB_SIZE 5 /* represent the first size table and its increment block size */
38
39/* CompositeMoniker data structure */
40typedef struct CompositeMonikerImpl{
45 IMoniker** tabMoniker; /* dynamic table containing all components (monikers) of this composite moniker */
46 ULONG tabSize; /* size of tabMoniker */
47 ULONG tabLastIndex; /* first free index in tabMoniker */
49
51{
52 return CONTAINING_RECORD(iface, CompositeMonikerImpl, IMoniker_iface);
53}
54
56{
57 return CONTAINING_RECORD(iface, CompositeMonikerImpl, IROTData_iface);
58}
59
61{
62 return CONTAINING_RECORD(iface, CompositeMonikerImpl, IMarshal_iface);
63}
64
65/* EnumMoniker data structure */
66typedef struct EnumMonikerImpl{
68 LONG ref;
69 IMoniker** tabMoniker; /* dynamic table containing the enumerated monikers */
70 ULONG tabSize; /* size of tabMoniker */
71 ULONG currentPos; /* index pointer on the current moniker */
73
75{
76 return CONTAINING_RECORD(iface, EnumMonikerImpl, IEnumMoniker_iface);
77}
78
79static HRESULT EnumMonikerImpl_CreateEnumMoniker(IMoniker** tabMoniker,ULONG tabSize,ULONG currentPos,BOOL leftToRight,IEnumMoniker ** ppmk);
80
81/*******************************************************************************
82 * CompositeMoniker_QueryInterface
83 *******************************************************************************/
84static HRESULT WINAPI
86{
88
89 TRACE("(%p,%s,%p)\n",This,debugstr_guid(riid),ppvObject);
90
91 /* Perform a sanity check on the parameters.*/
92 if ( ppvObject==0 )
93 return E_INVALIDARG;
94
95 /* Initialize the return parameter */
96 *ppvObject = 0;
97
98 /* Compare the riid with the interface IDs implemented by this object.*/
102 IsEqualIID(&IID_IMoniker, riid)
103 )
104 *ppvObject = iface;
105 else if (IsEqualIID(&IID_IROTData, riid))
106 *ppvObject = &This->IROTData_iface;
107 else if (IsEqualIID(&IID_IMarshal, riid))
108 *ppvObject = &This->IMarshal_iface;
109
110 /* Check that we obtained an interface.*/
111 if ((*ppvObject)==0)
112 return E_NOINTERFACE;
113
114 /* Query Interface always increases the reference count by one when it is successful */
115 IMoniker_AddRef(iface);
116
117 return S_OK;
118}
119
120/******************************************************************************
121 * CompositeMoniker_AddRef
122 ******************************************************************************/
123static ULONG WINAPI
125{
127
128 TRACE("(%p)\n",This);
129
130 return InterlockedIncrement(&This->ref);
131}
132
134{
135 ULONG i;
136
137 for (i = 0; i < This->tabLastIndex; i++)
138 IMoniker_Release(This->tabMoniker[i]);
139
140 This->tabLastIndex = 0;
141}
142
143/******************************************************************************
144 * CompositeMoniker_Release
145 ******************************************************************************/
146static ULONG WINAPI
148{
150 ULONG ref;
151
152 TRACE("(%p)\n",This);
153
155
156 /* destroy the object if there are no more references to it */
157 if (ref == 0){
158
159 /* release all the components before destroying this object */
161
162 HeapFree(GetProcessHeap(),0,This->tabMoniker);
164 }
165 return ref;
166}
167
168/******************************************************************************
169 * CompositeMoniker_GetClassID
170 ******************************************************************************/
171static HRESULT WINAPI
173{
174 TRACE("(%p,%p)\n",iface,pClassID);
175
176 if (pClassID==NULL)
177 return E_POINTER;
178
179 *pClassID = CLSID_CompositeMoniker;
180
181 return S_OK;
182}
183
184/******************************************************************************
185 * CompositeMoniker_IsDirty
186 ******************************************************************************/
187static HRESULT WINAPI
189{
190 /* Note that the OLE-provided implementations of the IPersistStream::IsDirty
191 method in the OLE-provided moniker interfaces always return S_FALSE because
192 their internal state never changes. */
193
194 TRACE("(%p)\n",iface);
195
196 return S_FALSE;
197}
198
199/******************************************************************************
200 * CompositeMoniker_Load
201 ******************************************************************************/
202static HRESULT WINAPI
204{
206 HRESULT res;
207 DWORD moniker_count;
208 DWORD i;
209
210 TRACE("(%p,%p)\n",iface,pStm);
211
212 /* this function call OleLoadFromStream function for each moniker within this object */
213
214 res=IStream_Read(pStm,&moniker_count,sizeof(DWORD),NULL);
215 if (res != S_OK)
216 {
217 ERR("couldn't reading moniker count from stream\n");
218 return E_FAIL;
219 }
220
222
223 for (i = 0; i < moniker_count; i++)
224 {
225 res=OleLoadFromStream(pStm,&IID_IMoniker,(void**)&This->tabMoniker[This->tabLastIndex]);
226 if (FAILED(res))
227 {
228 ERR("couldn't load moniker from stream, res = 0x%08x\n", res);
229 break;
230 }
231
232 /* resize the table if needed */
233 if (++This->tabLastIndex==This->tabSize){
234
235 This->tabSize+=BLOCK_TAB_SIZE;
236 This->tabMoniker=HeapReAlloc(GetProcessHeap(),0,This->tabMoniker,This->tabSize*sizeof(This->tabMoniker[0]));
237
238 if (This->tabMoniker==NULL)
239 return E_OUTOFMEMORY;
240 }
241 }
242
243 return res;
244}
245
246/******************************************************************************
247 * CompositeMoniker_Save
248 ******************************************************************************/
249static HRESULT WINAPI
251{
253 HRESULT res;
254 IEnumMoniker *enumMk;
255 IMoniker *pmk;
256 DWORD moniker_count = This->tabLastIndex;
257
258 TRACE("(%p,%p,%d)\n",iface,pStm,fClearDirty);
259
260 /* This function calls OleSaveToStream function for each moniker within
261 * this object.
262 * When I tested this function in windows, I usually found this constant
263 * at the beginning of the stream. I don't known why (there's no
264 * indication in the specification) !
265 */
266 res=IStream_Write(pStm,&moniker_count,sizeof(moniker_count),NULL);
267 if (FAILED(res)) return res;
268
269 IMoniker_Enum(iface,TRUE,&enumMk);
270
271 while(IEnumMoniker_Next(enumMk,1,&pmk,NULL)==S_OK){
272
274
275 IMoniker_Release(pmk);
276
277 if (FAILED(res)){
278
279 IEnumMoniker_Release(enumMk);
280 return res;
281 }
282 }
283
284 IEnumMoniker_Release(enumMk);
285
286 return S_OK;
287}
288
289/******************************************************************************
290 * CompositeMoniker_GetSizeMax
291 ******************************************************************************/
292static HRESULT WINAPI
294{
295 IEnumMoniker *enumMk;
296 IMoniker *pmk;
297 ULARGE_INTEGER ptmpSize;
298
299 /* The sizeMax of this object is calculated by calling GetSizeMax on
300 * each moniker within this object then summing all returned values
301 */
302
303 TRACE("(%p,%p)\n",iface,pcbSize);
304
305 if (!pcbSize)
306 return E_POINTER;
307
308 pcbSize->QuadPart = sizeof(DWORD);
309
310 IMoniker_Enum(iface,TRUE,&enumMk);
311
312 while(IEnumMoniker_Next(enumMk,1,&pmk,NULL)==S_OK){
313
314 IMoniker_GetSizeMax(pmk,&ptmpSize);
315
316 IMoniker_Release(pmk);
317
318 pcbSize->QuadPart = ptmpSize.QuadPart + sizeof(CLSID);
319 }
320
321 IEnumMoniker_Release(enumMk);
322
323 return S_OK;
324}
325
326/******************************************************************************
327 * CompositeMoniker_BindToObject
328 ******************************************************************************/
329static HRESULT WINAPI
331 IMoniker* pmkToLeft, REFIID riid, VOID** ppvResult)
332{
333 HRESULT res;
335 IMoniker *tempMk,*antiMk,*rightMostMk;
336 IEnumMoniker *enumMoniker;
337
338 TRACE("(%p,%p,%p,%s,%p)\n",iface,pbc,pmkToLeft,debugstr_guid(riid),ppvResult);
339
340 if (ppvResult==NULL)
341 return E_POINTER;
342
343 *ppvResult=0;
344 /* If pmkToLeft is NULL, this method looks for the moniker in the ROT, and if found, queries the retrieved */
345 /* object for the requested interface pointer. */
346 if(pmkToLeft==NULL){
347
348 res=IBindCtx_GetRunningObjectTable(pbc,&prot);
349
350 if (SUCCEEDED(res)){
351
352 /* if the requested class was loaded before ! we don't need to reload it */
353 res = IRunningObjectTable_GetObject(prot,iface,(IUnknown**)ppvResult);
354
355 if (res==S_OK)
356 return res;
357 }
358 }
359 else{
360 /* If pmkToLeft is not NULL, the method recursively calls IMoniker::BindToObject on the rightmost */
361 /* component of the composite, passing the rest of the composite as the pmkToLeft parameter for that call */
362
363 IMoniker_Enum(iface,FALSE,&enumMoniker);
364 IEnumMoniker_Next(enumMoniker,1,&rightMostMk,NULL);
365 IEnumMoniker_Release(enumMoniker);
366
367 res=CreateAntiMoniker(&antiMk);
368 res=IMoniker_ComposeWith(iface,antiMk,0,&tempMk);
369 IMoniker_Release(antiMk);
370
371 res=IMoniker_BindToObject(rightMostMk,pbc,tempMk,riid,ppvResult);
372
373 IMoniker_Release(tempMk);
374 IMoniker_Release(rightMostMk);
375 }
376
377 return res;
378}
379
380/******************************************************************************
381 * CompositeMoniker_BindToStorage
382 ******************************************************************************/
383static HRESULT WINAPI
385 IMoniker* pmkToLeft, REFIID riid, VOID** ppvResult)
386{
387 HRESULT res;
388 IMoniker *tempMk,*antiMk,*rightMostMk,*leftMk;
389 IEnumMoniker *enumMoniker;
390
391 TRACE("(%p,%p,%p,%s,%p)\n",iface,pbc,pmkToLeft,debugstr_guid(riid),ppvResult);
392
393 *ppvResult=0;
394
395 /* This method recursively calls BindToStorage on the rightmost component of the composite, */
396 /* passing the rest of the composite as the pmkToLeft parameter for that call. */
397
398 if (pmkToLeft)
399 {
400 res = IMoniker_ComposeWith(pmkToLeft, iface, FALSE, &leftMk);
401 if (FAILED(res)) return res;
402 }
403 else
404 leftMk = iface;
405
406 IMoniker_Enum(iface, FALSE, &enumMoniker);
407 IEnumMoniker_Next(enumMoniker, 1, &rightMostMk, NULL);
408 IEnumMoniker_Release(enumMoniker);
409
410 res = CreateAntiMoniker(&antiMk);
411 if (FAILED(res)) return res;
412 res = IMoniker_ComposeWith(leftMk, antiMk, 0, &tempMk);
413 if (FAILED(res)) return res;
414 IMoniker_Release(antiMk);
415
416 res = IMoniker_BindToStorage(rightMostMk, pbc, tempMk, riid, ppvResult);
417
418 IMoniker_Release(tempMk);
419
420 IMoniker_Release(rightMostMk);
421
422 if (pmkToLeft)
423 IMoniker_Release(leftMk);
424
425 return res;
426}
427
428/******************************************************************************
429 * CompositeMoniker_Reduce
430 ******************************************************************************/
431static HRESULT WINAPI
433 IMoniker** ppmkToLeft, IMoniker** ppmkReduced)
434{
435 HRESULT res;
436 IMoniker *tempMk,*antiMk,*rightMostMk,*leftReducedComposedMk,*rightMostReducedMk;
437 IEnumMoniker *enumMoniker;
438
439 TRACE("(%p,%p,%d,%p,%p)\n",iface,pbc,dwReduceHowFar,ppmkToLeft,ppmkReduced);
440
441 if (ppmkReduced==NULL)
442 return E_POINTER;
443
444 /* This method recursively calls Reduce for each of its component monikers. */
445
446 if (ppmkToLeft==NULL){
447
448 IMoniker_Enum(iface,FALSE,&enumMoniker);
449 IEnumMoniker_Next(enumMoniker,1,&rightMostMk,NULL);
450 IEnumMoniker_Release(enumMoniker);
451
452 CreateAntiMoniker(&antiMk);
453 IMoniker_ComposeWith(iface,antiMk,0,&tempMk);
454 IMoniker_Release(antiMk);
455
456 res = IMoniker_Reduce(rightMostMk,pbc,dwReduceHowFar,&tempMk, ppmkReduced);
457 IMoniker_Release(tempMk);
458 IMoniker_Release(rightMostMk);
459
460 return res;
461 }
462 else if (*ppmkToLeft==NULL)
463
464 return IMoniker_Reduce(iface,pbc,dwReduceHowFar,NULL,ppmkReduced);
465
466 else{
467
468 /* separate the composite moniker in to left and right moniker */
469 IMoniker_Enum(iface,FALSE,&enumMoniker);
470 IEnumMoniker_Next(enumMoniker,1,&rightMostMk,NULL);
471 IEnumMoniker_Release(enumMoniker);
472
473 CreateAntiMoniker(&antiMk);
474 IMoniker_ComposeWith(iface,antiMk,0,&tempMk);
475 IMoniker_Release(antiMk);
476
477 /* If any of the components reduces itself, the method returns S_OK and passes back a composite */
478 /* of the reduced components */
479 if (IMoniker_Reduce(rightMostMk,pbc,dwReduceHowFar,NULL,&rightMostReducedMk) &&
480 IMoniker_Reduce(rightMostMk,pbc,dwReduceHowFar,&tempMk,&leftReducedComposedMk) ){
481 IMoniker_Release(tempMk);
482 IMoniker_Release(rightMostMk);
483
484 return CreateGenericComposite(leftReducedComposedMk,rightMostReducedMk,ppmkReduced);
485 }
486 else{
487 /* If no reduction occurred, the method passes back the same moniker and returns MK_S_REDUCED_TO_SELF.*/
488 IMoniker_Release(tempMk);
489 IMoniker_Release(rightMostMk);
490
491 IMoniker_AddRef(iface);
492
493 *ppmkReduced=iface;
494
496 }
497 }
498}
499
500/******************************************************************************
501 * CompositeMoniker_ComposeWith
502 ******************************************************************************/
503static HRESULT WINAPI
505 BOOL fOnlyIfNotGeneric, IMoniker** ppmkComposite)
506{
507 TRACE("(%p,%p,%d,%p)\n",iface,pmkRight,fOnlyIfNotGeneric,ppmkComposite);
508
509 if ((ppmkComposite==NULL)||(pmkRight==NULL))
510 return E_POINTER;
511
512 *ppmkComposite=0;
513
514 /* If fOnlyIfNotGeneric is TRUE, this method sets *pmkComposite to NULL and returns MK_E_NEEDGENERIC; */
515 /* otherwise, the method returns the result of combining the two monikers by calling the */
516 /* CreateGenericComposite function */
517
518 if (fOnlyIfNotGeneric)
519 return MK_E_NEEDGENERIC;
520
521 return CreateGenericComposite(iface,pmkRight,ppmkComposite);
522}
523
524/******************************************************************************
525 * CompositeMoniker_Enum
526 ******************************************************************************/
527static HRESULT WINAPI
528CompositeMonikerImpl_Enum(IMoniker* iface,BOOL fForward, IEnumMoniker** ppenumMoniker)
529{
531
532 TRACE("(%p,%d,%p)\n",iface,fForward,ppenumMoniker);
533
534 if (ppenumMoniker == NULL)
535 return E_POINTER;
536
537 return EnumMonikerImpl_CreateEnumMoniker(This->tabMoniker,This->tabLastIndex,0,fForward,ppenumMoniker);
538}
539
540/******************************************************************************
541 * CompositeMoniker_IsEqual
542 ******************************************************************************/
543static HRESULT WINAPI
545{
546 IEnumMoniker *enumMoniker1,*enumMoniker2;
547 IMoniker *tempMk1,*tempMk2;
548 HRESULT res1,res2,res;
549 BOOL done;
550
551 TRACE("(%p,%p)\n",iface,pmkOtherMoniker);
552
553 if (pmkOtherMoniker==NULL)
554 return S_FALSE;
555
556 /* This method returns S_OK if the components of both monikers are equal when compared in the */
557 /* left-to-right order.*/
558 IMoniker_Enum(pmkOtherMoniker,TRUE,&enumMoniker1);
559
560 if (enumMoniker1==NULL)
561 return S_FALSE;
562
563 IMoniker_Enum(iface,TRUE,&enumMoniker2);
564
565 do {
566
567 res1=IEnumMoniker_Next(enumMoniker1,1,&tempMk1,NULL);
568 res2=IEnumMoniker_Next(enumMoniker2,1,&tempMk2,NULL);
569
570 if((res1==S_OK)&&(res2==S_OK)){
571 done = (res = IMoniker_IsEqual(tempMk1,tempMk2)) == S_FALSE;
572 }
573 else
574 {
575 res = (res1==S_FALSE) && (res2==S_FALSE);
576 done = TRUE;
577 }
578
579 if (res1==S_OK)
580 IMoniker_Release(tempMk1);
581
582 if (res2==S_OK)
583 IMoniker_Release(tempMk2);
584 } while (!done);
585
586 IEnumMoniker_Release(enumMoniker1);
587 IEnumMoniker_Release(enumMoniker2);
588
589 return res;
590}
591/******************************************************************************
592 * CompositeMoniker_Hash
593 ******************************************************************************/
594static HRESULT WINAPI
596{
597 IEnumMoniker *enumMoniker;
598 IMoniker *tempMk;
599 HRESULT res;
600 DWORD tempHash;
601
602 TRACE("(%p,%p)\n",iface,pdwHash);
603
604 if (pdwHash==NULL)
605 return E_POINTER;
606
607 res = IMoniker_Enum(iface,TRUE,&enumMoniker);
608 if(FAILED(res))
609 return res;
610
611 *pdwHash = 0;
612
613 while(IEnumMoniker_Next(enumMoniker,1,&tempMk,NULL)==S_OK){
614 res = IMoniker_Hash(tempMk, &tempHash);
615 if(FAILED(res))
616 break;
617 *pdwHash = *pdwHash ^ tempHash;
618
619 IMoniker_Release(tempMk);
620 }
621
622 IEnumMoniker_Release(enumMoniker);
623
624 return res;
625}
626
627/******************************************************************************
628 * CompositeMoniker_IsRunning
629 ******************************************************************************/
630static HRESULT WINAPI
632 IMoniker* pmkToLeft, IMoniker* pmkNewlyRunning)
633{
635 HRESULT res;
636 IMoniker *tempMk,*antiMk,*rightMostMk;
637 IEnumMoniker *enumMoniker;
638
639 TRACE("(%p,%p,%p,%p)\n",iface,pbc,pmkToLeft,pmkNewlyRunning);
640
641 /* If pmkToLeft is non-NULL, this method composes pmkToLeft with this moniker and calls IsRunning on the result.*/
642 if (pmkToLeft!=NULL){
643
644 CreateGenericComposite(pmkToLeft,iface,&tempMk);
645
646 res = IMoniker_IsRunning(tempMk,pbc,NULL,pmkNewlyRunning);
647
648 IMoniker_Release(tempMk);
649
650 return res;
651 }
652 else
653 /* If pmkToLeft is NULL, this method returns S_OK if pmkNewlyRunning is non-NULL and is equal */
654 /* to this moniker */
655
656 if (pmkNewlyRunning!=NULL)
657
658 if (IMoniker_IsEqual(iface,pmkNewlyRunning)==S_OK)
659 return S_OK;
660
661 else
662 return S_FALSE;
663
664 else{
665
666 if (pbc==NULL)
667 return E_INVALIDARG;
668
669 /* If pmkToLeft and pmkNewlyRunning are both NULL, this method checks the ROT to see whether */
670 /* the moniker is running. If so, the method returns S_OK; otherwise, it recursively calls */
671 /* IMoniker::IsRunning on the rightmost component of the composite, passing the remainder of */
672 /* the composite as the pmkToLeft parameter for that call. */
673
674 res=IBindCtx_GetRunningObjectTable(pbc,&rot);
675
676 if (FAILED(res))
677 return res;
678
679 res = IRunningObjectTable_IsRunning(rot,iface);
680 IRunningObjectTable_Release(rot);
681
682 if(res==S_OK)
683 return S_OK;
684
685 else{
686
687 IMoniker_Enum(iface,FALSE,&enumMoniker);
688 IEnumMoniker_Next(enumMoniker,1,&rightMostMk,NULL);
689 IEnumMoniker_Release(enumMoniker);
690
691 res=CreateAntiMoniker(&antiMk);
692 res=IMoniker_ComposeWith(iface,antiMk,0,&tempMk);
693 IMoniker_Release(antiMk);
694
695 res=IMoniker_IsRunning(rightMostMk,pbc,tempMk,pmkNewlyRunning);
696
697 IMoniker_Release(tempMk);
698 IMoniker_Release(rightMostMk);
699
700 return res;
701 }
702 }
703}
704
705/******************************************************************************
706 * CompositeMoniker_GetTimeOfLastChange
707 ******************************************************************************/
708static HRESULT WINAPI
710 IMoniker* pmkToLeft, FILETIME* pCompositeTime)
711{
712 HRESULT res;
713 IMoniker *tempMk,*antiMk,*rightMostMk,*leftMk;
714 IEnumMoniker *enumMoniker;
715
716 TRACE("(%p,%p,%p,%p)\n",iface,pbc,pmkToLeft,pCompositeTime);
717
718 if (pCompositeTime==NULL)
719 return E_INVALIDARG;
720
721 /* This method creates a composite of pmkToLeft (if non-NULL) and this moniker and uses the ROT to */
722 /* retrieve the time of last change. If the object is not in the ROT, the method recursively calls */
723 /* IMoniker::GetTimeOfLastChange on the rightmost component of the composite, passing the remainder */
724 /* of the composite as the pmkToLeft parameter for that call. */
725 if (pmkToLeft)
726 {
728
729 res = IMoniker_ComposeWith(pmkToLeft, iface, FALSE, &leftMk);
730 if (FAILED(res))
731 return res;
732
733 res = IBindCtx_GetRunningObjectTable(pbc,&rot);
734 if (FAILED(res))
735 {
736 IMoniker_Release(leftMk);
737 return res;
738 }
739
740 if (IRunningObjectTable_GetTimeOfLastChange(rot,leftMk,pCompositeTime)==S_OK)
741 {
742 IMoniker_Release(leftMk);
743 return res;
744 }
745 }
746 else
747 leftMk = iface;
748
749 IMoniker_Enum(iface, FALSE, &enumMoniker);
750 IEnumMoniker_Next(enumMoniker, 1, &rightMostMk, NULL);
751 IEnumMoniker_Release(enumMoniker);
752
753 res = CreateAntiMoniker(&antiMk);
754 res = IMoniker_ComposeWith(leftMk, antiMk, 0, &tempMk);
755 IMoniker_Release(antiMk);
756
757 res = IMoniker_GetTimeOfLastChange(rightMostMk, pbc, tempMk, pCompositeTime);
758
759 IMoniker_Release(tempMk);
760 IMoniker_Release(rightMostMk);
761
762 if (pmkToLeft)
763 IMoniker_Release(leftMk);
764
765 return res;
766}
767
768/******************************************************************************
769 * CompositeMoniker_Inverse
770 ******************************************************************************/
771static HRESULT WINAPI
773{
774 HRESULT res;
775 IMoniker *tempMk,*antiMk,*rightMostMk,*tempInvMk,*rightMostInvMk;
776 IEnumMoniker *enumMoniker;
777
778 TRACE("(%p,%p)\n",iface,ppmk);
779
780 if (ppmk==NULL)
781 return E_POINTER;
782
783 /* This method returns a composite moniker that consists of the inverses of each of the components */
784 /* of the original composite, stored in reverse order */
785
786 *ppmk = NULL;
787
788 res=CreateAntiMoniker(&antiMk);
789 if (FAILED(res))
790 return res;
791
792 res=IMoniker_ComposeWith(iface,antiMk,FALSE,&tempMk);
793 IMoniker_Release(antiMk);
794 if (FAILED(res))
795 return res;
796
797 if (tempMk==NULL)
798
799 return IMoniker_Inverse(iface,ppmk);
800
801 else{
802
803 IMoniker_Enum(iface,FALSE,&enumMoniker);
804 IEnumMoniker_Next(enumMoniker,1,&rightMostMk,NULL);
805 IEnumMoniker_Release(enumMoniker);
806
807 IMoniker_Inverse(rightMostMk,&rightMostInvMk);
808 CompositeMonikerImpl_Inverse(tempMk,&tempInvMk);
809
810 res=CreateGenericComposite(rightMostInvMk,tempInvMk,ppmk);
811
812 IMoniker_Release(tempMk);
813 IMoniker_Release(rightMostMk);
814 IMoniker_Release(tempInvMk);
815 IMoniker_Release(rightMostInvMk);
816
817 return res;
818 }
819}
820
821/******************************************************************************
822 * CompositeMoniker_CommonPrefixWith
823 ******************************************************************************/
824static HRESULT WINAPI
826 IMoniker** ppmkPrefix)
827{
828 DWORD mkSys;
829 HRESULT res1,res2;
830 IMoniker *tempMk1,*tempMk2,*mostLeftMk1,*mostLeftMk2;
831 IEnumMoniker *enumMoniker1,*enumMoniker2;
832 ULONG i,nbCommonMk=0;
833
834 /* If the other moniker is a composite, this method compares the components of each composite from left */
835 /* to right. The returned common prefix moniker might also be a composite moniker, depending on how many */
836 /* of the leftmost components were common to both monikers. */
837
838 if (ppmkPrefix==NULL)
839 return E_POINTER;
840
841 *ppmkPrefix=0;
842
843 if (pmkOther==NULL)
844 return MK_E_NOPREFIX;
845
846 IMoniker_IsSystemMoniker(pmkOther,&mkSys);
847
848 if(mkSys==MKSYS_GENERICCOMPOSITE){
849
850 IMoniker_Enum(iface,TRUE,&enumMoniker1);
851 IMoniker_Enum(pmkOther,TRUE,&enumMoniker2);
852
853 while(1){
854
855 res1=IEnumMoniker_Next(enumMoniker1,1,&mostLeftMk1,NULL);
856 res2=IEnumMoniker_Next(enumMoniker2,1,&mostLeftMk2,NULL);
857
858 if ((res1==S_FALSE) && (res2==S_FALSE)){
859
860 /* If the monikers are equal, the method returns MK_S_US and sets ppmkPrefix to this moniker.*/
861 *ppmkPrefix=iface;
862 IMoniker_AddRef(iface);
863 return MK_S_US;
864 }
865 else if ((res1==S_OK) && (res2==S_OK)){
866
867 if (IMoniker_IsEqual(mostLeftMk1,mostLeftMk2)==S_OK)
868
869 nbCommonMk++;
870
871 else
872 break;
873
874 }
875 else if (res1==S_OK){
876
877 /* If the other moniker is a prefix of this moniker, the method returns MK_S_HIM and sets */
878 /* ppmkPrefix to the other moniker. */
879 *ppmkPrefix=pmkOther;
880 return MK_S_HIM;
881 }
882 else{
883 /* If this moniker is a prefix of the other, this method returns MK_S_ME and sets ppmkPrefix */
884 /* to this moniker. */
885 *ppmkPrefix=iface;
886 return MK_S_ME;
887 }
888 }
889
890 IEnumMoniker_Release(enumMoniker1);
891 IEnumMoniker_Release(enumMoniker2);
892
893 /* If there is no common prefix, this method returns MK_E_NOPREFIX and sets ppmkPrefix to NULL. */
894 if (nbCommonMk==0)
895 return MK_E_NOPREFIX;
896
897 IEnumMoniker_Reset(enumMoniker1);
898
899 IEnumMoniker_Next(enumMoniker1,1,&tempMk1,NULL);
900
901 /* if we have more than one common moniker the result will be a composite moniker */
902 if (nbCommonMk>1){
903
904 /* initialize the common prefix moniker with the composite of two first moniker (from the left)*/
905 IEnumMoniker_Next(enumMoniker1,1,&tempMk2,NULL);
906 CreateGenericComposite(tempMk1,tempMk2,ppmkPrefix);
907 IMoniker_Release(tempMk1);
908 IMoniker_Release(tempMk2);
909
910 /* compose all common monikers in a composite moniker */
911 for(i=0;i<nbCommonMk;i++){
912
913 IEnumMoniker_Next(enumMoniker1,1,&tempMk1,NULL);
914
915 CreateGenericComposite(*ppmkPrefix,tempMk1,&tempMk2);
916
917 IMoniker_Release(*ppmkPrefix);
918
919 IMoniker_Release(tempMk1);
920
921 *ppmkPrefix=tempMk2;
922 }
923 return S_OK;
924 }
925 else{
926 /* if we have only one common moniker the result will be a simple moniker which is the most-left one*/
927 *ppmkPrefix=tempMk1;
928
929 return S_OK;
930 }
931 }
932 else{
933 /* If the other moniker is not a composite, the method simply compares it to the leftmost component
934 of this moniker.*/
935
936 IMoniker_Enum(iface,TRUE,&enumMoniker1);
937
938 IEnumMoniker_Next(enumMoniker1,1,&mostLeftMk1,NULL);
939
940 if (IMoniker_IsEqual(pmkOther,mostLeftMk1)==S_OK){
941
942 *ppmkPrefix=pmkOther;
943
944 return MK_S_HIM;
945 }
946 else
947 return MK_E_NOPREFIX;
948 }
949}
950
951/***************************************************************************************************
952 * GetAfterCommonPrefix (local function)
953 * This function returns a moniker that consist of the remainder when the common prefix is removed
954 ***************************************************************************************************/
955static VOID GetAfterCommonPrefix(IMoniker* pGenMk,IMoniker* commonMk,IMoniker** restMk)
956{
957 IMoniker *tempMk,*tempMk1,*tempMk2;
958 IEnumMoniker *enumMoniker1,*enumMoniker2,*enumMoniker3;
959 ULONG nbRestMk=0;
960 DWORD mkSys;
961 HRESULT res1,res2;
962
963 *restMk=0;
964
965 /* to create an enumerator for pGenMk with current position pointed on the first element after common */
966 /* prefix: enum the two monikers (left-right) then compare these enumerations (left-right) and stop */
967 /* on the first difference. */
968 IMoniker_Enum(pGenMk,TRUE,&enumMoniker1);
969
970 IMoniker_IsSystemMoniker(commonMk,&mkSys);
971
972 if (mkSys==MKSYS_GENERICCOMPOSITE){
973
974 IMoniker_Enum(commonMk,TRUE,&enumMoniker2);
975 while(1){
976
977 res1=IEnumMoniker_Next(enumMoniker1,1,&tempMk1,NULL);
978 res2=IEnumMoniker_Next(enumMoniker2,1,&tempMk2,NULL);
979
980 if ((res1==S_FALSE)||(res2==S_FALSE)){
981
982 if (res1==S_OK)
983
984 nbRestMk++;
985
986 IMoniker_Release(tempMk1);
987 IMoniker_Release(tempMk2);
988
989 break;
990 }
991 IMoniker_Release(tempMk1);
992 IMoniker_Release(tempMk2);
993 }
994 }
995 else{
996 IEnumMoniker_Next(enumMoniker1,1,&tempMk1,NULL);
997 IMoniker_Release(tempMk1);
998 }
999
1000 /* count the number of elements in the enumerator after the common prefix */
1001 IEnumMoniker_Clone(enumMoniker1,&enumMoniker3);
1002
1003 for(;IEnumMoniker_Next(enumMoniker3,1,&tempMk,NULL)==S_OK;nbRestMk++)
1004
1005 IMoniker_Release(tempMk);
1006
1007 if (nbRestMk==0)
1008 return;
1009
1010 /* create a generic composite moniker with monikers located after the common prefix */
1011 IEnumMoniker_Next(enumMoniker1,1,&tempMk1,NULL);
1012
1013 if (nbRestMk==1){
1014
1015 *restMk= tempMk1;
1016 return;
1017 }
1018 else {
1019
1020 IEnumMoniker_Next(enumMoniker1,1,&tempMk2,NULL);
1021
1022 CreateGenericComposite(tempMk1,tempMk2,restMk);
1023
1024 IMoniker_Release(tempMk1);
1025
1026 IMoniker_Release(tempMk2);
1027
1028 while(IEnumMoniker_Next(enumMoniker1,1,&tempMk1,NULL)==S_OK){
1029
1030 CreateGenericComposite(*restMk,tempMk1,&tempMk2);
1031
1032 IMoniker_Release(tempMk1);
1033
1034 IMoniker_Release(*restMk);
1035
1036 *restMk=tempMk2;
1037 }
1038 }
1039}
1040
1041/******************************************************************************
1042 * CompositeMoniker_RelativePathTo
1043 ******************************************************************************/
1044static HRESULT WINAPI
1046 IMoniker** ppmkRelPath)
1047{
1048 HRESULT res;
1049 IMoniker *restOtherMk=0,*restThisMk=0,*invRestThisMk=0,*commonMk=0;
1050
1051 TRACE("(%p,%p,%p)\n",iface,pmkOther,ppmkRelPath);
1052
1053 if (ppmkRelPath==NULL)
1054 return E_POINTER;
1055
1056 *ppmkRelPath=0;
1057
1058 /* This method finds the common prefix of the two monikers and creates two monikers that consist */
1059 /* of the remainder when the common prefix is removed. Then it creates the inverse for the remainder */
1060 /* of this moniker and composes the remainder of the other moniker on the right of it. */
1061
1062 /* finds the common prefix of the two monikers */
1063 res=IMoniker_CommonPrefixWith(iface,pmkOther,&commonMk);
1064
1065 /* if there's no common prefix or the two moniker are equal the relative is the other moniker */
1066 if ((res== MK_E_NOPREFIX)||(res==MK_S_US)){
1067
1068 *ppmkRelPath=pmkOther;
1069 IMoniker_AddRef(pmkOther);
1070 return MK_S_HIM;
1071 }
1072
1073 GetAfterCommonPrefix(iface,commonMk,&restThisMk);
1074 GetAfterCommonPrefix(pmkOther,commonMk,&restOtherMk);
1075
1076 /* if other is a prefix of this moniker the relative path is the inverse of the remainder path of this */
1077 /* moniker when the common prefix is removed */
1078 if (res==MK_S_HIM){
1079
1080 IMoniker_Inverse(restThisMk,ppmkRelPath);
1081 IMoniker_Release(restThisMk);
1082 }
1083 /* if this moniker is a prefix of other moniker the relative path is the remainder path of other moniker */
1084 /* when the common prefix is removed */
1085 else if (res==MK_S_ME){
1086
1087 *ppmkRelPath=restOtherMk;
1088 IMoniker_AddRef(restOtherMk);
1089 }
1090 /* the relative path is the inverse for the remainder of this moniker and the remainder of the other */
1091 /* moniker on the right of it. */
1092 else if (res==S_OK){
1093
1094 IMoniker_Inverse(restThisMk,&invRestThisMk);
1095 IMoniker_Release(restThisMk);
1096 CreateGenericComposite(invRestThisMk,restOtherMk,ppmkRelPath);
1097 IMoniker_Release(invRestThisMk);
1098 IMoniker_Release(restOtherMk);
1099 }
1100 return S_OK;
1101}
1102
1103/******************************************************************************
1104 * CompositeMoniker_GetDisplayName
1105 ******************************************************************************/
1106static HRESULT WINAPI
1108 IMoniker* pmkToLeft, LPOLESTR *ppszDisplayName)
1109{
1110 ULONG lengthStr=1;
1111 IEnumMoniker *enumMoniker;
1112 IMoniker* tempMk;
1113 LPOLESTR tempStr;
1114
1115 TRACE("(%p,%p,%p,%p)\n",iface,pbc,pmkToLeft,ppszDisplayName);
1116
1117 if (ppszDisplayName==NULL)
1118 return E_POINTER;
1119
1120 *ppszDisplayName=CoTaskMemAlloc(sizeof(WCHAR));
1121
1122 if (*ppszDisplayName==NULL)
1123 return E_OUTOFMEMORY;
1124
1125 /* This method returns the concatenation of the display names returned by each component moniker of */
1126 /* the composite */
1127
1128 **ppszDisplayName=0;
1129
1130 IMoniker_Enum(iface,TRUE,&enumMoniker);
1131
1132 while(IEnumMoniker_Next(enumMoniker,1,&tempMk,NULL)==S_OK){
1133
1134 IMoniker_GetDisplayName(tempMk,pbc,NULL,&tempStr);
1135
1136 lengthStr+=lstrlenW(tempStr);
1137
1138 *ppszDisplayName=CoTaskMemRealloc(*ppszDisplayName,lengthStr * sizeof(WCHAR));
1139
1140 if (*ppszDisplayName==NULL)
1141 return E_OUTOFMEMORY;
1142
1143 lstrcatW(*ppszDisplayName,tempStr);
1144
1145 CoTaskMemFree(tempStr);
1146 IMoniker_Release(tempMk);
1147 }
1148
1149 IEnumMoniker_Release(enumMoniker);
1150
1151 return S_OK;
1152}
1153
1154/******************************************************************************
1155 * CompositeMoniker_ParseDisplayName
1156 ******************************************************************************/
1157static HRESULT WINAPI
1159 IMoniker* pmkToLeft, LPOLESTR pszDisplayName, ULONG* pchEaten,
1160 IMoniker** ppmkOut)
1161{
1162 IEnumMoniker *enumMoniker;
1163 IMoniker *tempMk,*rightMostMk,*antiMk;
1164 /* This method recursively calls IMoniker::ParseDisplayName on the rightmost component of the composite,*/
1165 /* passing everything else as the pmkToLeft parameter for that call. */
1166
1167 /* get the most right moniker */
1168 IMoniker_Enum(iface,FALSE,&enumMoniker);
1169 IEnumMoniker_Next(enumMoniker,1,&rightMostMk,NULL);
1170 IEnumMoniker_Release(enumMoniker);
1171
1172 /* get the left moniker */
1173 CreateAntiMoniker(&antiMk);
1174 IMoniker_ComposeWith(iface,antiMk,0,&tempMk);
1175 IMoniker_Release(antiMk);
1176
1177 return IMoniker_ParseDisplayName(rightMostMk,pbc,tempMk,pszDisplayName,pchEaten,ppmkOut);
1178}
1179
1180/******************************************************************************
1181 * CompositeMoniker_IsSystemMoniker
1182 ******************************************************************************/
1183static HRESULT WINAPI
1185{
1186 TRACE("(%p,%p)\n",iface,pwdMksys);
1187
1188 if (!pwdMksys)
1189 return E_POINTER;
1190
1191 (*pwdMksys)=MKSYS_GENERICCOMPOSITE;
1192
1193 return S_OK;
1194}
1195
1196/*******************************************************************************
1197 * CompositeMonikerIROTData_QueryInterface
1198 *******************************************************************************/
1199static HRESULT WINAPI
1201 VOID** ppvObject)
1202{
1204
1205 TRACE("(%p,%s,%p)\n",iface,debugstr_guid(riid),ppvObject);
1206
1207 return CompositeMonikerImpl_QueryInterface(&This->IMoniker_iface, riid, ppvObject);
1208}
1209
1210/***********************************************************************
1211 * CompositeMonikerIROTData_AddRef
1212 */
1213static ULONG WINAPI
1215{
1217
1218 TRACE("(%p)\n",iface);
1219
1220 return IMoniker_AddRef(&This->IMoniker_iface);
1221}
1222
1223/***********************************************************************
1224 * CompositeMonikerIROTData_Release
1225 */
1227{
1229
1230 TRACE("(%p)\n",iface);
1231
1232 return IMoniker_Release(&This->IMoniker_iface);
1233}
1234
1235/******************************************************************************
1236 * CompositeMonikerIROTData_GetComparisonData
1237 ******************************************************************************/
1238static HRESULT WINAPI
1240 BYTE* pbData, ULONG cbMax, ULONG* pcbData)
1241{
1243 IEnumMoniker *pEnumMk;
1244 IMoniker *pmk;
1245 HRESULT hr;
1246
1247 TRACE("(%p, %u, %p)\n", pbData, cbMax, pcbData);
1248
1249 *pcbData = sizeof(CLSID);
1250
1251 hr = IMoniker_Enum(&This->IMoniker_iface, TRUE, &pEnumMk);
1252 if (FAILED(hr)) return hr;
1253
1254 while(IEnumMoniker_Next(pEnumMk, 1, &pmk, NULL) == S_OK)
1255 {
1256 IROTData *pROTData;
1257 hr = IMoniker_QueryInterface(pmk, &IID_IROTData, (void **)&pROTData);
1258 if (FAILED(hr))
1259 ERR("moniker doesn't support IROTData interface\n");
1260
1261 if (SUCCEEDED(hr))
1262 {
1263 ULONG cbData;
1264 hr = IROTData_GetComparisonData(pROTData, NULL, 0, &cbData);
1265 IROTData_Release(pROTData);
1266 if (SUCCEEDED(hr) || (hr == E_OUTOFMEMORY))
1267 {
1268 *pcbData += cbData;
1269 hr = S_OK;
1270 }
1271 else
1272 ERR("IROTData_GetComparisonData failed with error 0x%08x\n", hr);
1273 }
1274
1275 IMoniker_Release(pmk);
1276
1277 if (FAILED(hr))
1278 {
1279 IEnumMoniker_Release(pEnumMk);
1280 return hr;
1281 }
1282 }
1283 if (cbMax < *pcbData)
1284 return E_OUTOFMEMORY;
1285
1286 IEnumMoniker_Reset(pEnumMk);
1287
1288 memcpy(pbData, &CLSID_CompositeMoniker, sizeof(CLSID));
1289 pbData += sizeof(CLSID);
1290 cbMax -= sizeof(CLSID);
1291
1292 while (IEnumMoniker_Next(pEnumMk, 1, &pmk, NULL) == S_OK)
1293 {
1294 IROTData *pROTData;
1295 hr = IMoniker_QueryInterface(pmk, &IID_IROTData, (void **)&pROTData);
1296 if (FAILED(hr))
1297 ERR("moniker doesn't support IROTData interface\n");
1298
1299 if (SUCCEEDED(hr))
1300 {
1301 ULONG cbData;
1302 hr = IROTData_GetComparisonData(pROTData, pbData, cbMax, &cbData);
1303 IROTData_Release(pROTData);
1304 if (SUCCEEDED(hr))
1305 {
1306 pbData += cbData;
1307 cbMax -= cbData;
1308 }
1309 else
1310 ERR("IROTData_GetComparisonData failed with error 0x%08x\n", hr);
1311 }
1312
1313 IMoniker_Release(pmk);
1314
1315 if (FAILED(hr))
1316 {
1317 IEnumMoniker_Release(pEnumMk);
1318 return hr;
1319 }
1320 }
1321
1322 IEnumMoniker_Release(pEnumMk);
1323
1324 return S_OK;
1325}
1326
1328{
1330
1331 TRACE("(%p,%s,%p)\n",iface,debugstr_guid(riid),ppv);
1332
1333 return CompositeMonikerImpl_QueryInterface(&This->IMoniker_iface, riid, ppv);
1334}
1335
1337{
1339
1340 TRACE("(%p)\n",iface);
1341
1342 return CompositeMonikerImpl_AddRef(&This->IMoniker_iface);
1343}
1344
1346{
1348
1349 TRACE("(%p)\n",iface);
1350
1351 return CompositeMonikerImpl_Release(&This->IMoniker_iface);
1352}
1353
1355 IMarshal *iface, REFIID riid, void *pv, DWORD dwDestContext,
1356 void* pvDestContext, DWORD mshlflags, CLSID* pCid)
1357{
1359
1360 TRACE("(%s, %p, %x, %p, %x, %p)\n", debugstr_guid(riid), pv,
1361 dwDestContext, pvDestContext, mshlflags, pCid);
1362
1363 return IMoniker_GetClassID(&This->IMoniker_iface, pCid);
1364}
1365
1367 IMarshal *iface, REFIID riid, void *pv, DWORD dwDestContext,
1368 void* pvDestContext, DWORD mshlflags, DWORD* pSize)
1369{
1371 IEnumMoniker *pEnumMk;
1372 IMoniker *pmk;
1373 HRESULT hr;
1375
1376 TRACE("(%s, %p, %x, %p, %x, %p)\n", debugstr_guid(riid), pv,
1377 dwDestContext, pvDestContext, mshlflags, pSize);
1378
1379 *pSize = 0x10; /* to match native */
1380
1381 hr = IMoniker_Enum(&This->IMoniker_iface, TRUE, &pEnumMk);
1382 if (FAILED(hr)) return hr;
1383
1384 hr = IMoniker_GetSizeMax(&This->IMoniker_iface, &size);
1385
1386 while (IEnumMoniker_Next(pEnumMk, 1, &pmk, NULL) == S_OK)
1387 {
1388 ULONG size;
1389
1390 hr = CoGetMarshalSizeMax(&size, &IID_IMoniker, (IUnknown *)pmk, dwDestContext, pvDestContext, mshlflags);
1391 if (SUCCEEDED(hr))
1392 *pSize += size;
1393
1394 IMoniker_Release(pmk);
1395
1396 if (FAILED(hr))
1397 {
1398 IEnumMoniker_Release(pEnumMk);
1399 return hr;
1400 }
1401 }
1402
1403 IEnumMoniker_Release(pEnumMk);
1404
1405 return S_OK;
1406}
1407
1409 REFIID riid, void* pv, DWORD dwDestContext,
1410 void* pvDestContext, DWORD mshlflags)
1411{
1413 IEnumMoniker *pEnumMk;
1414 IMoniker *pmk;
1415 HRESULT hr;
1416 ULONG i = 0;
1417
1418 TRACE("(%p, %s, %p, %x, %p, %x)\n", pStm, debugstr_guid(riid), pv,
1419 dwDestContext, pvDestContext, mshlflags);
1420
1421 hr = IMoniker_Enum(&This->IMoniker_iface, TRUE, &pEnumMk);
1422 if (FAILED(hr)) return hr;
1423
1424 while (IEnumMoniker_Next(pEnumMk, 1, &pmk, NULL) == S_OK)
1425 {
1426 hr = CoMarshalInterface(pStm, &IID_IMoniker, (IUnknown *)pmk, dwDestContext, pvDestContext, mshlflags);
1427
1428 IMoniker_Release(pmk);
1429
1430 if (FAILED(hr))
1431 {
1432 IEnumMoniker_Release(pEnumMk);
1433 return hr;
1434 }
1435 i++;
1436 }
1437
1438 if (i != 2)
1439 FIXME("moniker count of %d not supported\n", i);
1440
1441 IEnumMoniker_Release(pEnumMk);
1442
1443 return S_OK;
1444}
1445
1447 REFIID riid, void **ppv)
1448{
1450 HRESULT hr;
1451
1452 TRACE("(%p, %s, %p)\n", pStm, debugstr_guid(riid), ppv);
1453
1455
1456 /* resize the table if needed */
1457 if (This->tabLastIndex + 2 > This->tabSize)
1458 {
1459 This->tabSize += max(BLOCK_TAB_SIZE, 2);
1460 This->tabMoniker=HeapReAlloc(GetProcessHeap(),0,This->tabMoniker,This->tabSize*sizeof(This->tabMoniker[0]));
1461
1462 if (This->tabMoniker==NULL)
1463 return E_OUTOFMEMORY;
1464 }
1465
1466 hr = CoUnmarshalInterface(pStm, &IID_IMoniker, (void**)&This->tabMoniker[This->tabLastIndex]);
1467 if (FAILED(hr))
1468 {
1469 ERR("couldn't unmarshal moniker, hr = 0x%08x\n", hr);
1470 return hr;
1471 }
1472 This->tabLastIndex++;
1473 hr = CoUnmarshalInterface(pStm, &IID_IMoniker, (void**)&This->tabMoniker[This->tabLastIndex]);
1474 if (FAILED(hr))
1475 {
1476 ERR("couldn't unmarshal moniker, hr = 0x%08x\n", hr);
1477 return hr;
1478 }
1479 This->tabLastIndex++;
1480
1481 return IMoniker_QueryInterface(&This->IMoniker_iface, riid, ppv);
1482}
1483
1485{
1486 TRACE("(%p)\n", pStm);
1487 /* can't release a state-based marshal as nothing on server side to
1488 * release */
1489 return S_OK;
1490}
1491
1494{
1495 TRACE("(0x%x)\n", dwReserved);
1496 /* can't disconnect a state-based marshal as nothing on server side to
1497 * disconnect from */
1498 return S_OK;
1499}
1500
1501/******************************************************************************
1502 * EnumMonikerImpl_QueryInterface
1503 ******************************************************************************/
1504static HRESULT WINAPI
1506{
1508
1509 TRACE("(%p,%s,%p)\n",This,debugstr_guid(riid),ppvObject);
1510
1511 /* Perform a sanity check on the parameters.*/
1512 if ( ppvObject==0 )
1513 return E_INVALIDARG;
1514
1515 /* Initialize the return parameter */
1516 *ppvObject = 0;
1517
1518 /* Compare the riid with the interface IDs implemented by this object.*/
1520 *ppvObject = iface;
1521
1522 /* Check that we obtained an interface.*/
1523 if ((*ppvObject)==0)
1524 return E_NOINTERFACE;
1525
1526 /* Query Interface always increases the reference count by one when it is successful */
1527 IEnumMoniker_AddRef(iface);
1528
1529 return S_OK;
1530}
1531
1532/******************************************************************************
1533 * EnumMonikerImpl_AddRef
1534 ******************************************************************************/
1535static ULONG WINAPI
1537{
1539
1540 TRACE("(%p)\n",This);
1541
1542 return InterlockedIncrement(&This->ref);
1543
1544}
1545
1546/******************************************************************************
1547 * EnumMonikerImpl_Release
1548 ******************************************************************************/
1549static ULONG WINAPI
1551{
1553 ULONG i;
1554 ULONG ref;
1555 TRACE("(%p)\n",This);
1556
1557 ref = InterlockedDecrement(&This->ref);
1558
1559 /* destroy the object if there are no more references to it */
1560 if (ref == 0) {
1561
1562 for(i=0;i<This->tabSize;i++)
1563 IMoniker_Release(This->tabMoniker[i]);
1564
1565 HeapFree(GetProcessHeap(),0,This->tabMoniker);
1567 }
1568 return ref;
1569}
1570
1571/******************************************************************************
1572 * EnumMonikerImpl_Next
1573 ******************************************************************************/
1574static HRESULT WINAPI
1576 ULONG* pceltFethed)
1577{
1579 ULONG i;
1580
1581 /* retrieve the requested number of moniker from the current position */
1582 for(i=0;((This->currentPos < This->tabSize) && (i < celt));i++)
1583 {
1584 rgelt[i]=This->tabMoniker[This->currentPos++];
1585 IMoniker_AddRef(rgelt[i]);
1586 }
1587
1588 if (pceltFethed!=NULL)
1589 *pceltFethed= i;
1590
1591 if (i==celt)
1592 return S_OK;
1593 else
1594 return S_FALSE;
1595}
1596
1597/******************************************************************************
1598 * EnumMonikerImpl_Skip
1599 ******************************************************************************/
1600static HRESULT WINAPI
1602{
1604
1605 if ((This->currentPos+celt) >= This->tabSize)
1606 return S_FALSE;
1607
1608 This->currentPos+=celt;
1609
1610 return S_OK;
1611}
1612
1613/******************************************************************************
1614 * EnumMonikerImpl_Reset
1615 ******************************************************************************/
1616static HRESULT WINAPI
1618{
1620
1621 This->currentPos=0;
1622
1623 return S_OK;
1624}
1625
1626/******************************************************************************
1627 * EnumMonikerImpl_Clone
1628 ******************************************************************************/
1629static HRESULT WINAPI
1631{
1633
1634 return EnumMonikerImpl_CreateEnumMoniker(This->tabMoniker,This->tabSize,This->currentPos,TRUE,ppenum);
1635}
1636
1637/********************************************************************************/
1638/* Virtual function table for the IROTData class */
1639static const IEnumMonikerVtbl VT_EnumMonikerImpl =
1640{
1648};
1649
1650/******************************************************************************
1651 * EnumMonikerImpl_CreateEnumMoniker
1652 ******************************************************************************/
1653static HRESULT
1655 ULONG currentPos, BOOL leftToRight, IEnumMoniker ** ppmk)
1656{
1657 EnumMonikerImpl* newEnumMoniker;
1658 ULONG i;
1659
1660 if (currentPos > tabSize)
1661 return E_INVALIDARG;
1662
1663 newEnumMoniker = HeapAlloc(GetProcessHeap(), 0, sizeof(EnumMonikerImpl));
1664
1665 if (newEnumMoniker == 0)
1667
1668 /* Initialize the virtual function table. */
1669 newEnumMoniker->IEnumMoniker_iface.lpVtbl = &VT_EnumMonikerImpl;
1670 newEnumMoniker->ref = 1;
1671
1672 newEnumMoniker->tabSize=tabSize;
1673 newEnumMoniker->currentPos=currentPos;
1674
1675 newEnumMoniker->tabMoniker=HeapAlloc(GetProcessHeap(),0,tabSize*sizeof(newEnumMoniker->tabMoniker[0]));
1676
1677 if (newEnumMoniker->tabMoniker==NULL) {
1678 HeapFree(GetProcessHeap(), 0, newEnumMoniker);
1679 return E_OUTOFMEMORY;
1680 }
1681
1682 if (leftToRight)
1683 for (i=0;i<tabSize;i++){
1684
1685 newEnumMoniker->tabMoniker[i]=tabMoniker[i];
1686 IMoniker_AddRef(tabMoniker[i]);
1687 }
1688 else
1689 for (i = tabSize; i > 0; i--){
1690
1691 newEnumMoniker->tabMoniker[tabSize-i]=tabMoniker[i - 1];
1692 IMoniker_AddRef(tabMoniker[i - 1]);
1693 }
1694
1695 *ppmk=&newEnumMoniker->IEnumMoniker_iface;
1696
1697 return S_OK;
1698}
1699
1700/********************************************************************************/
1701/* Virtual function table for the CompositeMonikerImpl class which includes */
1702/* IPersist, IPersistStream and IMoniker functions. */
1703
1704static const IMonikerVtbl VT_CompositeMonikerImpl =
1705{
1729};
1730
1731/********************************************************************************/
1732/* Virtual function table for the IROTData class. */
1733static const IROTDataVtbl VT_ROTDataImpl =
1734{
1739};
1740
1741static const IMarshalVtbl VT_MarshalImpl =
1742{
1752};
1753
1754/******************************************************************************
1755 * Composite-Moniker_Construct (local function)
1756 *******************************************************************************/
1757static HRESULT
1759{
1760 DWORD mkSys;
1761 IEnumMoniker *enumMoniker;
1762 IMoniker *tempMk;
1763 HRESULT res;
1765 int i;
1766
1767 This = HeapAlloc(GetProcessHeap(), 0, sizeof(*This));
1768
1769 if (!This)
1770 return E_OUTOFMEMORY;
1771
1772 TRACE("(%p,%p,%p)\n",This,pmkFirst,pmkRest);
1773
1774 /* Initialize the virtual function table. */
1775 This->IMoniker_iface.lpVtbl = &VT_CompositeMonikerImpl;
1776 This->IROTData_iface.lpVtbl = &VT_ROTDataImpl;
1777 This->IMarshal_iface.lpVtbl = &VT_MarshalImpl;
1778 This->ref = 1;
1779
1780 This->tabSize=BLOCK_TAB_SIZE;
1781 This->tabLastIndex=0;
1782
1783 This->tabMoniker=HeapAlloc(GetProcessHeap(),0,This->tabSize*sizeof(This->tabMoniker[0]));
1784 if (This->tabMoniker==NULL) {
1786 return E_OUTOFMEMORY;
1787 }
1788
1789 if (!pmkFirst && !pmkRest)
1790 {
1791 *ppMoniker = &This->IMoniker_iface;
1792 return S_OK;
1793 }
1794
1795 IMoniker_IsSystemMoniker(pmkFirst,&mkSys);
1796
1797 /* put the first moniker contents in the beginning of the table */
1798 if (mkSys!=MKSYS_GENERICCOMPOSITE){
1799
1800 This->tabMoniker[(This->tabLastIndex)++]=pmkFirst;
1801 IMoniker_AddRef(pmkFirst);
1802 }
1803 else{
1804
1805 IMoniker_Enum(pmkFirst,TRUE,&enumMoniker);
1806
1807 while(IEnumMoniker_Next(enumMoniker,1,&This->tabMoniker[This->tabLastIndex],NULL)==S_OK){
1808
1809
1810 if (++This->tabLastIndex==This->tabSize){
1811 IMoniker **tab_moniker = This->tabMoniker;
1812
1813 This->tabSize+=BLOCK_TAB_SIZE;
1814 This->tabMoniker=HeapReAlloc(GetProcessHeap(),0,This->tabMoniker,This->tabSize*sizeof(This->tabMoniker[0]));
1815
1816 if (This->tabMoniker==NULL){
1817 for (i = 0; i < This->tabLastIndex; i++)
1818 IMoniker_Release(tab_moniker[i]);
1819 HeapFree(GetProcessHeap(), 0, tab_moniker);
1821 return E_OUTOFMEMORY;
1822 }
1823 }
1824 }
1825
1826 IEnumMoniker_Release(enumMoniker);
1827 }
1828
1829 /* put the rest moniker contents after the first one and make simplification if needed */
1830
1831 IMoniker_IsSystemMoniker(pmkRest,&mkSys);
1832
1833 if (mkSys!=MKSYS_GENERICCOMPOSITE){
1834
1835 /* add a simple moniker to the moniker table */
1836
1837 res=IMoniker_ComposeWith(This->tabMoniker[This->tabLastIndex-1],pmkRest,TRUE,&tempMk);
1838
1839 if (res==MK_E_NEEDGENERIC){
1840
1841 /* there's no simplification in this case */
1842 This->tabMoniker[This->tabLastIndex]=pmkRest;
1843
1844 This->tabLastIndex++;
1845
1846 IMoniker_AddRef(pmkRest);
1847 }
1848 else if (tempMk==NULL){
1849
1850 /* we have an antimoniker after a simple moniker so we can make a simplification in this case */
1851 IMoniker_Release(This->tabMoniker[This->tabLastIndex-1]);
1852
1853 This->tabLastIndex--;
1854 }
1855 else if (SUCCEEDED(res)){
1856
1857 /* the non-generic composition was successful so we can make a simplification in this case */
1858 IMoniker_Release(This->tabMoniker[This->tabLastIndex-1]);
1859
1860 This->tabMoniker[This->tabLastIndex-1]=tempMk;
1861 } else{
1862 for (i = 0; i < This->tabLastIndex; i++)
1863 IMoniker_Release(This->tabMoniker[i]);
1864 HeapFree(GetProcessHeap(), 0, This->tabMoniker);
1866 return res;
1867 }
1868
1869 /* resize tabMoniker if needed */
1870 if (This->tabLastIndex==This->tabSize){
1871 IMoniker **tab_moniker = This->tabMoniker;
1872
1873 This->tabSize+=BLOCK_TAB_SIZE;
1874
1875 This->tabMoniker=HeapReAlloc(GetProcessHeap(),0,This->tabMoniker,This->tabSize*sizeof(IMoniker));
1876
1877 if (This->tabMoniker==NULL){
1878 for (i = 0; i < This->tabLastIndex; i++)
1879 IMoniker_Release(tab_moniker[i]);
1880 HeapFree(GetProcessHeap(), 0, tab_moniker);
1882 return E_OUTOFMEMORY;
1883 }
1884 }
1885 }
1886 else{
1887
1888 /* add a composite moniker to the moniker table (do the same thing
1889 * for each moniker within the composite moniker as a simple moniker
1890 * (see above for how to add a simple moniker case) )
1891 */
1892 IMoniker_Enum(pmkRest,TRUE,&enumMoniker);
1893
1894 while(IEnumMoniker_Next(enumMoniker,1,&This->tabMoniker[This->tabLastIndex],NULL)==S_OK){
1895
1896 res=IMoniker_ComposeWith(This->tabMoniker[This->tabLastIndex-1],This->tabMoniker[This->tabLastIndex],TRUE,&tempMk);
1897
1898 if (res==MK_E_NEEDGENERIC){
1899
1900 This->tabLastIndex++;
1901 }
1902 else if (tempMk==NULL){
1903
1904 IMoniker_Release(This->tabMoniker[This->tabLastIndex-1]);
1905 IMoniker_Release(This->tabMoniker[This->tabLastIndex]);
1906 This->tabLastIndex--;
1907 }
1908 else{
1909
1910 IMoniker_Release(This->tabMoniker[This->tabLastIndex-1]);
1911
1912 This->tabMoniker[This->tabLastIndex-1]=tempMk;
1913 }
1914
1915 if (This->tabLastIndex==This->tabSize){
1916 IMoniker **tab_moniker = This->tabMoniker;
1917
1918 This->tabSize+=BLOCK_TAB_SIZE;
1919
1920 This->tabMoniker=HeapReAlloc(GetProcessHeap(),0,This->tabMoniker,This->tabSize*sizeof(This->tabMoniker[0]));
1921
1922 if (This->tabMoniker==NULL){
1923 for (i = 0; i < This->tabLastIndex; i++)
1924 IMoniker_Release(tab_moniker[i]);
1925 HeapFree(GetProcessHeap(), 0, tab_moniker);
1927 return E_OUTOFMEMORY;
1928 }
1929 }
1930 }
1931
1932 IEnumMoniker_Release(enumMoniker);
1933 }
1934
1935 /* only one moniker, then just return it */
1936 if (This->tabLastIndex == 1)
1937 {
1938 *ppMoniker = This->tabMoniker[0];
1939 IMoniker_AddRef(*ppMoniker);
1940 IMoniker_Release(&This->IMoniker_iface);
1941 }
1942 else
1943 *ppMoniker = &This->IMoniker_iface;
1944
1945 return S_OK;
1946}
1947
1948/******************************************************************************
1949 * CreateGenericComposite [OLE32.@]
1950 ******************************************************************************/
1952CreateGenericComposite(IMoniker *pmkFirst, IMoniker *pmkRest, IMoniker **ppmkComposite)
1953{
1954 IMoniker* moniker = 0;
1955 HRESULT hr = S_OK;
1956
1957 TRACE("(%p,%p,%p)\n",pmkFirst,pmkRest,ppmkComposite);
1958
1959 if (ppmkComposite==NULL)
1960 return E_POINTER;
1961
1962 *ppmkComposite=0;
1963
1964 if (pmkFirst==NULL && pmkRest!=NULL){
1965
1966 *ppmkComposite=pmkRest;
1967 IMoniker_AddRef(pmkRest);
1968 return S_OK;
1969 }
1970 else if (pmkFirst!=NULL && pmkRest==NULL){
1971 *ppmkComposite=pmkFirst;
1972 IMoniker_AddRef(pmkFirst);
1973 return S_OK;
1974 }
1975 else if (pmkFirst==NULL && pmkRest==NULL)
1976 return S_OK;
1977
1978 hr = CompositeMonikerImpl_Construct(&moniker,pmkFirst,pmkRest);
1979
1980 if (FAILED(hr))
1981 return hr;
1982
1983 hr = IMoniker_QueryInterface(moniker,&IID_IMoniker,(void**)ppmkComposite);
1984 IMoniker_Release(moniker);
1985
1986 return hr;
1987}
1988
1989/******************************************************************************
1990 * MonikerCommonPrefixWith [OLE32.@]
1991 ******************************************************************************/
1993MonikerCommonPrefixWith(IMoniker* pmkThis,IMoniker* pmkOther,IMoniker** ppmkCommon)
1994{
1995 FIXME("(),stub!\n");
1996 return E_NOTIMPL;
1997}
1998
2000 IUnknown *pUnk, REFIID riid, void **ppv)
2001{
2002 IMoniker* pMoniker;
2003 HRESULT hr;
2004
2005 TRACE("(%p, %s, %p)\n", pUnk, debugstr_guid(riid), ppv);
2006
2007 *ppv = NULL;
2008
2009 if (pUnk)
2010 return CLASS_E_NOAGGREGATION;
2011
2013
2014 if (SUCCEEDED(hr))
2015 {
2016 hr = IMoniker_QueryInterface(pMoniker, riid, ppv);
2017 IMoniker_Release(pMoniker);
2018 }
2019
2020 return hr;
2021}
GLfloat rot
Definition: 3dtext.c:36
HRESULT WINAPI CreateAntiMoniker(IMoniker **ppmk)
Definition: antimoniker.c:608
#define InterlockedIncrement
Definition: armddk.h:53
#define InterlockedDecrement
Definition: armddk.h:52
#define WINE_DEFAULT_DEBUG_CHANNEL(t)
Definition: precomp.h:23
#define FIXME(fmt,...)
Definition: precomp.h:53
#define ERR(fmt,...)
Definition: precomp.h:57
const GUID IID_IUnknown
static HRESULT CompositeMonikerImpl_Construct(IMoniker **ppMoniker, IMoniker *pmkFirst, IMoniker *pmkRest)
static CompositeMonikerImpl * impl_from_IMarshal(IMarshal *iface)
static HRESULT WINAPI CompositeMonikerMarshalImpl_DisconnectObject(IMarshal *iface, DWORD dwReserved)
static HRESULT WINAPI CompositeMonikerImpl_ComposeWith(IMoniker *iface, IMoniker *pmkRight, BOOL fOnlyIfNotGeneric, IMoniker **ppmkComposite)
static CompositeMonikerImpl * impl_from_IMoniker(IMoniker *iface)
static HRESULT WINAPI CompositeMonikerImpl_GetDisplayName(IMoniker *iface, IBindCtx *pbc, IMoniker *pmkToLeft, LPOLESTR *ppszDisplayName)
static HRESULT WINAPI CompositeMonikerImpl_IsRunning(IMoniker *iface, IBindCtx *pbc, IMoniker *pmkToLeft, IMoniker *pmkNewlyRunning)
#define BLOCK_TAB_SIZE
static ULONG WINAPI CompositeMonikerImpl_Release(IMoniker *iface)
static const IMonikerVtbl VT_CompositeMonikerImpl
static const IMarshalVtbl VT_MarshalImpl
HRESULT WINAPI MonikerCommonPrefixWith(IMoniker *pmkThis, IMoniker *pmkOther, IMoniker **ppmkCommon)
static HRESULT WINAPI EnumMonikerImpl_Reset(IEnumMoniker *iface)
static HRESULT WINAPI CompositeMonikerROTDataImpl_GetComparisonData(IROTData *iface, BYTE *pbData, ULONG cbMax, ULONG *pcbData)
static EnumMonikerImpl * impl_from_IEnumMoniker(IEnumMoniker *iface)
static HRESULT WINAPI CompositeMonikerImpl_Save(IMoniker *iface, IStream *pStm, BOOL fClearDirty)
static ULONG WINAPI EnumMonikerImpl_Release(IEnumMoniker *iface)
static HRESULT WINAPI CompositeMonikerImpl_GetSizeMax(IMoniker *iface, ULARGE_INTEGER *pcbSize)
static HRESULT WINAPI EnumMonikerImpl_Clone(IEnumMoniker *iface, IEnumMoniker **ppenum)
static CompositeMonikerImpl * impl_from_IROTData(IROTData *iface)
static HRESULT WINAPI CompositeMonikerImpl_RelativePathTo(IMoniker *iface, IMoniker *pmkOther, IMoniker **ppmkRelPath)
static HRESULT WINAPI CompositeMonikerImpl_IsSystemMoniker(IMoniker *iface, DWORD *pwdMksys)
static ULONG WINAPI CompositeMonikerMarshalImpl_AddRef(IMarshal *iface)
static HRESULT WINAPI CompositeMonikerROTDataImpl_QueryInterface(IROTData *iface, REFIID riid, VOID **ppvObject)
static HRESULT WINAPI CompositeMonikerMarshalImpl_UnmarshalInterface(IMarshal *iface, IStream *pStm, REFIID riid, void **ppv)
struct EnumMonikerImpl EnumMonikerImpl
static HRESULT WINAPI CompositeMonikerImpl_Enum(IMoniker *iface, BOOL fForward, IEnumMoniker **ppenumMoniker)
static HRESULT WINAPI EnumMonikerImpl_Skip(IEnumMoniker *iface, ULONG celt)
static HRESULT WINAPI CompositeMonikerMarshalImpl_QueryInterface(IMarshal *iface, REFIID riid, LPVOID *ppv)
static HRESULT WINAPI CompositeMonikerMarshalImpl_MarshalInterface(IMarshal *iface, IStream *pStm, REFIID riid, void *pv, DWORD dwDestContext, void *pvDestContext, DWORD mshlflags)
static HRESULT WINAPI CompositeMonikerImpl_BindToStorage(IMoniker *iface, IBindCtx *pbc, IMoniker *pmkToLeft, REFIID riid, VOID **ppvResult)
static ULONG WINAPI CompositeMonikerImpl_AddRef(IMoniker *iface)
HRESULT WINAPI CompositeMoniker_CreateInstance(IClassFactory *iface, IUnknown *pUnk, REFIID riid, void **ppv)
static ULONG WINAPI CompositeMonikerMarshalImpl_Release(IMarshal *iface)
static const IROTDataVtbl VT_ROTDataImpl
static HRESULT WINAPI EnumMonikerImpl_Next(IEnumMoniker *iface, ULONG celt, IMoniker **rgelt, ULONG *pceltFethed)
static ULONG WINAPI CompositeMonikerROTDataImpl_AddRef(IROTData *iface)
static void CompositeMonikerImpl_ReleaseMonikersInTable(CompositeMonikerImpl *This)
static HRESULT WINAPI CompositeMonikerImpl_GetTimeOfLastChange(IMoniker *iface, IBindCtx *pbc, IMoniker *pmkToLeft, FILETIME *pCompositeTime)
static VOID GetAfterCommonPrefix(IMoniker *pGenMk, IMoniker *commonMk, IMoniker **restMk)
static HRESULT WINAPI CompositeMonikerImpl_Hash(IMoniker *iface, DWORD *pdwHash)
static HRESULT WINAPI CompositeMonikerImpl_CommonPrefixWith(IMoniker *iface, IMoniker *pmkOther, IMoniker **ppmkPrefix)
static HRESULT WINAPI CompositeMonikerImpl_Reduce(IMoniker *iface, IBindCtx *pbc, DWORD dwReduceHowFar, IMoniker **ppmkToLeft, IMoniker **ppmkReduced)
static HRESULT WINAPI CompositeMonikerImpl_GetClassID(IMoniker *iface, CLSID *pClassID)
static HRESULT WINAPI CompositeMonikerImpl_BindToObject(IMoniker *iface, IBindCtx *pbc, IMoniker *pmkToLeft, REFIID riid, VOID **ppvResult)
static HRESULT WINAPI CompositeMonikerImpl_IsEqual(IMoniker *iface, IMoniker *pmkOtherMoniker)
static HRESULT WINAPI CompositeMonikerImpl_Load(IMoniker *iface, IStream *pStm)
static HRESULT WINAPI CompositeMonikerMarshalImpl_GetUnmarshalClass(IMarshal *iface, REFIID riid, void *pv, DWORD dwDestContext, void *pvDestContext, DWORD mshlflags, CLSID *pCid)
static HRESULT WINAPI CompositeMonikerImpl_IsDirty(IMoniker *iface)
static HRESULT WINAPI CompositeMonikerImpl_ParseDisplayName(IMoniker *iface, IBindCtx *pbc, IMoniker *pmkToLeft, LPOLESTR pszDisplayName, ULONG *pchEaten, IMoniker **ppmkOut)
static HRESULT WINAPI CompositeMonikerImpl_Inverse(IMoniker *iface, IMoniker **ppmk)
HRESULT WINAPI CreateGenericComposite(IMoniker *pmkFirst, IMoniker *pmkRest, IMoniker **ppmkComposite)
static ULONG WINAPI EnumMonikerImpl_AddRef(IEnumMoniker *iface)
static HRESULT WINAPI CompositeMonikerImpl_QueryInterface(IMoniker *iface, REFIID riid, void **ppvObject)
static HRESULT WINAPI CompositeMonikerMarshalImpl_GetMarshalSizeMax(IMarshal *iface, REFIID riid, void *pv, DWORD dwDestContext, void *pvDestContext, DWORD mshlflags, DWORD *pSize)
static HRESULT WINAPI CompositeMonikerMarshalImpl_ReleaseMarshalData(IMarshal *iface, IStream *pStm)
static HRESULT EnumMonikerImpl_CreateEnumMoniker(IMoniker **tabMoniker, ULONG tabSize, ULONG currentPos, BOOL leftToRight, IEnumMoniker **ppmk)
static HRESULT WINAPI EnumMonikerImpl_QueryInterface(IEnumMoniker *iface, REFIID riid, void **ppvObject)
static ULONG WINAPI CompositeMonikerROTDataImpl_Release(IROTData *iface)
static const IEnumMonikerVtbl VT_EnumMonikerImpl
#define E_OUTOFMEMORY
Definition: ddrawi.h:100
#define E_INVALIDARG
Definition: ddrawi.h:101
#define E_NOTIMPL
Definition: ddrawi.h:99
#define E_FAIL
Definition: ddrawi.h:102
#define NULL
Definition: types.h:112
#define TRUE
Definition: types.h:120
#define FALSE
Definition: types.h:117
#define GetProcessHeap()
Definition: compat.h:736
#define HeapAlloc
Definition: compat.h:733
#define HeapReAlloc
Definition: compat.h:734
#define HeapFree(x, y, z)
Definition: compat.h:735
#define lstrlenW
Definition: compat.h:750
HRESULT WINAPI CoUnmarshalInterface(IStream *pStream, REFIID riid, LPVOID *ppv)
Definition: marshal.c:1981
HRESULT WINAPI CoGetMarshalSizeMax(ULONG *pulSize, REFIID riid, IUnknown *pUnk, DWORD dwDestContext, void *pvDestContext, DWORD mshlFlags)
Definition: marshal.c:1800
HRESULT WINAPI CoMarshalInterface(IStream *pStream, REFIID riid, IUnknown *pUnk, DWORD dwDestContext, void *pvDestContext, DWORD mshlFlags)
Definition: marshal.c:1876
HRESULT WINAPI OleLoadFromStream(IStream *pStm, REFIID iidInterface, void **ppvObj)
Definition: storage32.c:9129
HRESULT WINAPI OleSaveToStream(IPersistStream *pPStm, IStream *pStm)
Definition: storage32.c:9164
static void *static void *static LPDIRECTPLAY IUnknown * pUnk
Definition: dplayx.c:30
unsigned int BOOL
Definition: ntddk_ex.h:94
unsigned long DWORD
Definition: ntddk_ex.h:95
GLsizeiptr size
Definition: glext.h:5919
GLuint res
Definition: glext.h:9613
GLsizei GLenum const GLvoid GLsizei GLenum GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLint GLint GLint GLshort GLshort GLshort GLubyte GLubyte GLubyte GLuint GLuint GLuint GLushort GLushort GLushort GLbyte GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLfloat GLint GLint GLint GLint GLshort GLshort GLshort GLshort GLubyte GLubyte GLubyte GLubyte GLuint GLuint GLuint GLuint GLushort GLushort GLushort GLushort GLboolean const GLdouble const GLfloat const GLint const GLshort const GLbyte const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLdouble const GLfloat const GLfloat const GLint const GLint const GLshort const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort GLenum GLenum GLenum GLfloat GLenum GLint GLenum GLenum GLenum GLfloat GLenum GLenum GLint GLenum GLfloat GLenum GLint GLint GLushort GLenum GLenum GLfloat GLenum GLenum GLint GLfloat const GLubyte GLenum GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLint GLint GLsizei GLsizei GLint GLenum GLenum const GLvoid GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLenum const GLdouble GLenum GLenum const GLfloat GLenum GLenum const GLint GLsizei GLuint GLfloat GLuint GLbitfield GLfloat GLint GLuint GLboolean GLenum GLfloat GLenum GLbitfield GLenum GLfloat GLfloat GLint GLint const GLfloat GLenum GLfloat GLfloat GLint GLint GLfloat GLfloat GLint GLint const GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat const GLdouble const GLfloat const GLdouble const GLfloat GLint i
Definition: glfuncs.h:248
LPVOID WINAPI CoTaskMemRealloc(LPVOID pvOld, SIZE_T size)
Definition: ifs.c:460
VOID WINAPI CoTaskMemFree(LPVOID ptr)
Definition: ifs.c:442
LPVOID WINAPI CoTaskMemAlloc(SIZE_T size)
Definition: ifs.c:426
REFIID riid
Definition: atlbase.h:39
REFIID LPVOID * ppv
Definition: atlbase.h:39
#define S_OK
Definition: intsafe.h:52
#define SUCCEEDED(hr)
Definition: intsafe.h:50
#define FAILED(hr)
Definition: intsafe.h:51
#define debugstr_guid
Definition: kernel32.h:35
LPWSTR WINAPI lstrcatW(LPWSTR lpString1, LPCWSTR lpString2)
Definition: lstring.c:274
#define memcpy(s1, s2, n)
Definition: mkisofs.h:878
static LPOLESTR
Definition: stg_prop.c:27
IID CLSID
Definition: mstsclib_i.c:62
_In_ HANDLE _In_ DWORD _In_ DWORD _Inout_opt_ LPOVERLAPPED _In_opt_ LPTRANSMIT_FILE_BUFFERS _In_ DWORD dwReserved
Definition: mswsock.h:95
#define DWORD
Definition: nt_native.h:44
const GUID IID_IEnumMoniker
long LONG
Definition: pedump.c:60
const GUID IID_IPersist
Definition: proxy.cpp:14
const GUID IID_IPersistStream
Definition: proxy.cpp:13
#define IsEqualIID(riid1, riid2)
Definition: guiddef.h:95
#define REFIID
Definition: guiddef.h:118
HRESULT hr
Definition: shlfolder.c:183
#define TRACE(s)
Definition: solgame.cpp:4
IEnumMoniker IEnumMoniker_iface
Definition: mediacatenum.c:36
IMoniker ** tabMoniker
ULONGLONG QuadPart
Definition: ms-dtyp.idl:185
Definition: main.c:40
Definition: send.c:48
#define max(a, b)
Definition: svc.c:63
#define CONTAINING_RECORD(address, type, field)
Definition: typedefs.h:260
uint32_t ULONG
Definition: typedefs.h:59
_In_ HCRYPTHASH _In_ BOOL _In_ DWORD _Inout_updates_bytes_to_ pdwDataLen BYTE * pbData
Definition: wincrypt.h:4201
_In_ void _In_ PCCERT_CONTEXT _In_opt_ LPFILETIME _In_ DWORD _In_ DWORD _Outptr_opt_ void ** ppvObject
Definition: wincrypt.h:6082
_In_ DWORD _Out_writes_bytes_to_opt_ pcbData void _Inout_ DWORD * pcbData
Definition: wincrypt.h:4950
#define WINAPI
Definition: msvc.h:6
#define S_FALSE
Definition: winerror.h:2357
#define MK_S_REDUCED_TO_SELF
Definition: winerror.h:2773
#define E_NOINTERFACE
Definition: winerror.h:2364
#define MK_E_NOPREFIX
Definition: winerror.h:2795
#define CLASS_E_NOAGGREGATION
Definition: winerror.h:2662
#define MK_S_ME
Definition: winerror.h:2774
#define MK_E_NEEDGENERIC
Definition: winerror.h:2783
#define MK_S_HIM
Definition: winerror.h:2775
#define E_POINTER
Definition: winerror.h:2365
#define STG_E_INSUFFICIENTMEMORY
Definition: winerror.h:2570
#define MK_S_US
Definition: winerror.h:2776
__wchar_t WCHAR
Definition: xmlstorage.h:180
unsigned char BYTE
Definition: xxhash.c:193