ReactOS 0.4.16-dev-2332-g4cba65d
itemmoniker.c
Go to the documentation of this file.
1/*
2 * ItemMonikers 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#include "winerror.h"
27#include "windef.h"
28#include "winbase.h"
29#include "winuser.h"
30#include "winnls.h"
31#include "wine/debug.h"
32#include "ole2.h"
33#include "moniker.h"
34
36
37/* ItemMoniker data structure */
38typedef struct ItemMonikerImpl{
39 IMoniker IMoniker_iface; /* VTable relative to the IMoniker interface.*/
40 IROTData IROTData_iface; /* VTable relative to the IROTData interface.*/
42 LPOLESTR itemName; /* item name identified by this ItemMoniker */
43 LPOLESTR itemDelimiter; /* Delimiter string */
44 IUnknown *pMarshal; /* custom marshaler */
46
48{
49 return CONTAINING_RECORD(iface, ItemMonikerImpl, IMoniker_iface);
50}
51
53
55{
56 return CONTAINING_RECORD(iface, ItemMonikerImpl, IROTData_iface);
57}
58
60{
64};
65
67{
68 return CONTAINING_RECORD(iface, struct container_lock, IUnknown_iface);
69}
70
72{
74 {
75 *obj = iface;
76 IUnknown_AddRef(iface);
77 return S_OK;
78 }
79
80 WARN("Unsupported interface %s.\n", debugstr_guid(riid));
81 *obj = NULL;
82 return E_NOINTERFACE;
83}
84
86{
88 return InterlockedIncrement(&lock->refcount);
89}
90
92{
95
96 if (!refcount)
97 {
98 IOleItemContainer_LockContainer(lock->container, FALSE);
99 IOleItemContainer_Release(lock->container);
100 free(lock);
101 }
102
103 return refcount;
104}
105
106static const IUnknownVtbl container_lock_vtbl =
107{
111};
112
114{
115 struct container_lock *lock;
116 HRESULT hr;
117
118 if (!(lock = malloc(sizeof(*lock))))
119 return E_OUTOFMEMORY;
120
121 if (FAILED(hr = IOleItemContainer_LockContainer(container, TRUE)))
122 {
123 free(lock);
124 return hr;
125 }
126
127 lock->IUnknown_iface.lpVtbl = &container_lock_vtbl;
128 lock->refcount = 1;
129 lock->container = container;
130 IOleItemContainer_AddRef(lock->container);
131
132 hr = IBindCtx_RegisterObjectBound(pbc, &lock->IUnknown_iface);
133 IUnknown_Release(&lock->IUnknown_iface);
134 return hr;
135}
136
137/*******************************************************************************
138 * ItemMoniker_QueryInterface
139 *******************************************************************************/
141{
143
144 TRACE("%p, %s, %p.\n", iface, debugstr_guid(riid), ppvObject);
145
146 if (!ppvObject)
147 return E_INVALIDARG;
148
152 IsEqualIID(&IID_IMoniker, riid) ||
153 IsEqualGUID(&CLSID_ItemMoniker, riid))
154 {
155 *ppvObject = iface;
156 }
157 else if (IsEqualIID(&IID_IROTData, riid))
158 *ppvObject = &This->IROTData_iface;
159 else if (IsEqualIID(&IID_IMarshal, riid))
160 {
161 HRESULT hr = S_OK;
162 if (!This->pMarshal)
163 hr = MonikerMarshal_Create(iface, &This->pMarshal);
164 if (hr != S_OK)
165 return hr;
166 return IUnknown_QueryInterface(This->pMarshal, riid, ppvObject);
167 }
168 else
169 {
170 *ppvObject = NULL;
171 return E_NOINTERFACE;
172 }
173
174 IMoniker_AddRef(iface);
175 return S_OK;
176}
177
178/******************************************************************************
179 * ItemMoniker_AddRef
180 ******************************************************************************/
182{
184
185 TRACE("(%p)\n",This);
186
187 return InterlockedIncrement(&This->ref);
188}
189
190/******************************************************************************
191 * ItemMoniker_Release
192 ******************************************************************************/
194{
197
198 TRACE("%p, refcount %lu.\n", iface, refcount);
199
200 if (!refcount)
201 {
202 if (moniker->pMarshal) IUnknown_Release(moniker->pMarshal);
203 free(moniker->itemName);
204 free(moniker->itemDelimiter);
205 free(moniker);
206 }
207
208 return refcount;
209}
210
211/******************************************************************************
212 * ItemMoniker_GetClassID
213 ******************************************************************************/
215{
216 TRACE("(%p,%p)\n",iface,pClassID);
217
218 if (pClassID==NULL)
219 return E_POINTER;
220
221 *pClassID = CLSID_ItemMoniker;
222
223 return S_OK;
224}
225
226/******************************************************************************
227 * ItemMoniker_IsDirty
228 ******************************************************************************/
230{
231 /* Note that the OLE-provided implementations of the IPersistStream::IsDirty
232 method in the OLE-provided moniker interfaces always return S_FALSE because
233 their internal state never changes. */
234
235 TRACE("(%p)\n",iface);
236
237 return S_FALSE;
238}
239
241{
242 DWORD str_len, read_len, lenW, i;
243 HRESULT hr = S_OK;
244 char *buffer;
245 WCHAR *str;
246
247 IStream_Read(stream, &str_len, sizeof(str_len), &read_len);
248 if (read_len != sizeof(str_len))
249 return E_FAIL;
250
251 if (!str_len)
252 {
253 free(*ret);
254 *ret = NULL;
255 return S_OK;
256 }
257
258 if (!(buffer = malloc(str_len)))
259 return E_OUTOFMEMORY;
260
261 IStream_Read(stream, buffer, str_len, &read_len);
262 if (read_len != str_len)
263 {
264 free(buffer);
265 return E_FAIL;
266 }
267
268 /* Skip ansi buffer, it must be null terminated. */
269 i = 0;
270 while (i < str_len && buffer[i])
271 i++;
272
273 if (buffer[i])
274 {
275 WARN("Expected null terminated ansi name.\n");
276 hr = E_FAIL;
277 goto end;
278 }
279
280 if (i < str_len - 1)
281 {
282 str_len -= i + 1;
283
284 if (str_len % sizeof(WCHAR))
285 {
286 WARN("Unexpected Unicode name length %ld.\n", str_len);
287 hr = E_FAIL;
288 goto end;
289 }
290
291 str = malloc(str_len + sizeof(WCHAR));
292 if (str)
293 {
294 memcpy(str, &buffer[i + 1], str_len);
295 str[str_len / sizeof(WCHAR)] = 0;
296 }
297 }
298 else
299 {
300 lenW = MultiByteToWideChar(CP_ACP, 0, buffer, -1, NULL, 0);
301 str = malloc(lenW * sizeof(WCHAR));
302 if (str)
303 MultiByteToWideChar(CP_ACP, 0, buffer, -1, str, lenW);
304 }
305
306 if (str)
307 {
308 free(*ret);
309 *ret = str;
310 }
311 else
313
314end:
315 free(buffer);
316
317 return hr;
318}
319
320/******************************************************************************
321 * ItemMoniker_Load
322 ******************************************************************************/
324{
326 HRESULT hr;
327
328 TRACE("(%p, %p)\n", iface, stream);
329
330 /* Delimiter and name use the same record structure: 4 bytes byte-length field, followed by
331 string data. Data starts with single byte null-terminated string, WCHAR non-terminated
332 string optionally follows. Length of WCHAR string is determined as a difference between total
333 byte-length and single byte string length. */
334
335 hr = item_moniker_load_string_record(stream, &This->itemDelimiter);
336 if (SUCCEEDED(hr))
338
339 return hr;
340}
341
342/******************************************************************************
343 * ItemMoniker_Save
344 ******************************************************************************/
346{
348 int str_len;
349 HRESULT hr;
350 char *str;
351
352 TRACE("(%p, %p, %d)\n", iface, stream, fClearDirty);
353
354 /* data written by this function are : 1) DWORD : size of item delimiter string ('\0' included ) */
355 /* 2) String (type A): item delimiter string ('\0' included) */
356 /* 3) DWORD : size of item name string ('\0' included) */
357 /* 4) String (type A): item name string ('\0' included) */
358 if (This->itemDelimiter)
359 {
360 str_len = WideCharToMultiByte(CP_ACP, 0, This->itemDelimiter, -1, NULL, 0, NULL, NULL);
361 str = malloc(str_len);
362 WideCharToMultiByte(CP_ACP, 0, This->itemDelimiter, -1, str, str_len, NULL, NULL);
363
364 hr = IStream_Write(stream, &str_len, sizeof(str_len), NULL);
365 hr = IStream_Write(stream, str, str_len, NULL);
366
367 free(str);
368 }
369 else
370 {
371 str_len = 0;
372 hr = IStream_Write(stream, &str_len, sizeof(str_len), NULL);
373 }
374
375 str_len = WideCharToMultiByte(CP_ACP, 0, This->itemName, -1, NULL, 0, NULL, NULL);
376 str = malloc(str_len);
377 WideCharToMultiByte(CP_ACP, 0, This->itemName, -1, str, str_len, NULL, NULL);
378 hr = IStream_Write(stream, &str_len, sizeof(str_len), NULL);
379 hr = IStream_Write(stream, str, str_len, NULL);
380 free(str);
381
382 return hr;
383}
384
385/******************************************************************************
386 * ItemMoniker_GetSizeMax
387 ******************************************************************************/
389{
391 DWORD nameLength=lstrlenW(This->itemName)+1;
392
393 TRACE("(%p,%p)\n",iface,pcbSize);
394
395 if (!pcbSize)
396 return E_POINTER;
397
398 /* for more details see ItemMonikerImpl_Save comments */
399
400 pcbSize->u.LowPart = sizeof(DWORD) + /* DWORD which contains delimiter length */
401 sizeof(DWORD) + /* DWORD which contains item name length */
402 nameLength*4 + /* item name string */
403 18; /* strange, but true */
404 if (This->itemDelimiter)
405 pcbSize->u.LowPart += (lstrlenW(This->itemDelimiter) + 1) * 4;
406
407 pcbSize->u.HighPart=0;
408
409 return S_OK;
410}
411
413{
414 DWORD bind_speed = BINDSPEED_INDEFINITE;
415 BIND_OPTS bind_opts;
416
417 bind_opts.cbStruct = sizeof(bind_opts);
418 if (SUCCEEDED(IBindCtx_GetBindOptions(pbc, &bind_opts)) && bind_opts.dwTickCountDeadline)
419 bind_speed = bind_opts.dwTickCountDeadline < 2500 ? BINDSPEED_IMMEDIATE : BINDSPEED_MODERATE;
420
421 return bind_speed;
422}
423
424/******************************************************************************
425 * ItemMoniker_BindToObject
426 ******************************************************************************/
428 IBindCtx* pbc,
429 IMoniker* pmkToLeft,
430 REFIID riid,
431 VOID** ppvResult)
432{
435 HRESULT hr;
436
437 TRACE("(%p,%p,%p,%s,%p)\n",iface,pbc,pmkToLeft,debugstr_guid(riid),ppvResult);
438
439 if(ppvResult ==NULL)
440 return E_POINTER;
441
442 if(pmkToLeft==NULL)
443 return E_INVALIDARG;
444
445 *ppvResult=0;
446
447 hr = IMoniker_BindToObject(pmkToLeft, pbc, NULL, &IID_IOleItemContainer, (void **)&container);
448 if (SUCCEEDED(hr))
449 {
451 WARN("Failed to lock container, hr %#lx.\n", hr);
452
453 hr = IOleItemContainer_GetObject(container, This->itemName, get_bind_speed_from_bindctx(pbc), pbc,
454 riid, ppvResult);
455 IOleItemContainer_Release(container);
456 }
457
458 return hr;
459}
460
461/******************************************************************************
462 * ItemMoniker_BindToStorage
463 ******************************************************************************/
465 void **ppvResult)
466{
469 HRESULT hr;
470
471 TRACE("%p, %p, %p, %s, %p.\n", iface, pbc, pmkToLeft, debugstr_guid(riid), ppvResult);
472
473 *ppvResult = 0;
474
475 if (!pmkToLeft)
476 return E_INVALIDARG;
477
478 hr = IMoniker_BindToObject(pmkToLeft, pbc, NULL, &IID_IOleItemContainer, (void **)&container);
479 if (SUCCEEDED(hr))
480 {
482 WARN("Failed to lock container, hr %#lx.\n", hr);
483
484 hr = IOleItemContainer_GetObjectStorage(container, moniker->itemName, pbc, riid, ppvResult);
485 IOleItemContainer_Release(container);
486 }
487
488 return hr;
489}
490
492 DWORD dwReduceHowFar, IMoniker** ppmkToLeft, IMoniker** ppmkReduced)
493{
494 TRACE("%p, %p, %ld, %p, %p.\n", iface, pbc, dwReduceHowFar, ppmkToLeft, ppmkReduced);
495
496 if (ppmkReduced==NULL)
497 return E_POINTER;
498
500
501 *ppmkReduced=iface;
502
504}
505
507 BOOL only_if_not_generic, IMoniker **result)
508{
509 DWORD order;
510
511 TRACE("%p, %p, %d, %p\n", iface, right, only_if_not_generic, result);
512
513 if (!result || !right)
514 return E_POINTER;
515
516 *result = NULL;
517
519 return order > 1 ? create_anti_moniker(order - 1, result) : S_OK;
520
521 return only_if_not_generic ? MK_E_NEEDGENERIC : CreateGenericComposite(iface, right, result);
522}
523
524/******************************************************************************
525 * ItemMoniker_Enum
526 ******************************************************************************/
527static HRESULT WINAPI ItemMonikerImpl_Enum(IMoniker* iface,BOOL fForward, IEnumMoniker** ppenumMoniker)
528{
529 TRACE("(%p,%d,%p)\n",iface,fForward,ppenumMoniker);
530
531 if (ppenumMoniker == NULL)
532 return E_POINTER;
533
534 *ppenumMoniker = NULL;
535
536 return S_OK;
537}
538
539/******************************************************************************
540 * ItemMoniker_IsEqual
541 ******************************************************************************/
543{
544 ItemMonikerImpl *moniker = impl_from_IMoniker(iface), *other_moniker;
545
546 TRACE("%p, %p.\n", iface, other);
547
548 if (!other)
549 return E_INVALIDARG;
550
551 other_moniker = unsafe_impl_from_IMoniker(other);
552 if (!other_moniker)
553 return S_FALSE;
554
555 return !wcsicmp(moniker->itemName, other_moniker->itemName) ? S_OK : S_FALSE;
556}
557
558/******************************************************************************
559 * ItemMoniker_Hash
560 ******************************************************************************/
562{
564 DWORD h = 0;
565 int i,len;
566 int off = 0;
568
569 if (pdwHash==NULL)
570 return E_POINTER;
571
572 val = This->itemName;
573 len = lstrlenW(val);
574
575 for (i = len ; i > 0; i--)
576 h = (h * 3) ^ towupper(val[off++]);
577
578 *pdwHash=h;
579
580 return S_OK;
581}
582
583/******************************************************************************
584 * ItemMoniker_IsRunning
585 ******************************************************************************/
587 IMoniker *pmkNewlyRunning)
588{
592 HRESULT hr;
593
594 TRACE("(%p,%p,%p,%p)\n",iface,pbc,pmkToLeft,pmkNewlyRunning);
595
596 if (!pbc)
597 return E_INVALIDARG;
598
599 if (!pmkToLeft)
600 {
601 if (pmkNewlyRunning)
602 {
603 return IMoniker_IsEqual(iface, pmkNewlyRunning);
604 }
605 else
606 {
607 hr = IBindCtx_GetRunningObjectTable(pbc, &rot);
608 if (SUCCEEDED(hr))
609 {
610 hr = IRunningObjectTable_IsRunning(rot, iface);
611 IRunningObjectTable_Release(rot);
612 }
613 }
614 }
615 else
616 {
617 /* Container itself must be running too. */
618 hr = IMoniker_IsRunning(pmkToLeft, pbc, NULL, NULL);
619 if (hr != S_OK)
620 return hr;
621
622 hr = IMoniker_BindToObject(pmkToLeft, pbc, NULL, &IID_IOleItemContainer, (void **)&container);
623 if (SUCCEEDED(hr))
624 {
625 hr = IOleItemContainer_IsRunning(container, moniker->itemName);
626 IOleItemContainer_Release(container);
627 }
628 }
629
630 return hr;
631}
632
633/******************************************************************************
634 * ItemMoniker_GetTimeOfLastChange
635 ******************************************************************************/
637 IBindCtx* pbc,
638 IMoniker* pmkToLeft,
639 FILETIME* pItemTime)
640{
642 HRESULT res;
643 IMoniker *compositeMk;
644
645 TRACE("(%p,%p,%p,%p)\n",iface,pbc,pmkToLeft,pItemTime);
646
647 if (pItemTime==NULL)
648 return E_INVALIDARG;
649
650 /* If pmkToLeft is NULL, this method returns MK_E_NOTBINDABLE */
651 if (pmkToLeft==NULL)
652
653 return MK_E_NOTBINDABLE;
654 else {
655
656 /* Otherwise, the method creates a composite of pmkToLeft and this moniker and uses the ROT to access */
657 /* the time of last change. If the object is not in the ROT, the method calls */
658 /* IMoniker::GetTimeOfLastChange on the pmkToLeft parameter. */
659
660 res=CreateGenericComposite(pmkToLeft,iface,&compositeMk);
661 if (FAILED(res))
662 return res;
663
664 res=IBindCtx_GetRunningObjectTable(pbc,&rot);
665 if (FAILED(res)) {
666 IMoniker_Release(compositeMk);
667 return res;
668 }
669
670 if (IRunningObjectTable_GetTimeOfLastChange(rot,compositeMk,pItemTime)!=S_OK)
671
672 res=IMoniker_GetTimeOfLastChange(pmkToLeft,pbc,NULL,pItemTime);
673
674 IMoniker_Release(compositeMk);
675 }
676
677 return res;
678}
679
680/******************************************************************************
681 * ItemMoniker_Inverse
682 ******************************************************************************/
684{
685 TRACE("(%p,%p)\n",iface,ppmk);
686
687 if (ppmk==NULL)
688 return E_POINTER;
689
690 return CreateAntiMoniker(ppmk);
691}
692
695{
696 TRACE("%p, %p, %p\n", iface, other, prefix);
697
698 if (IMoniker_IsEqual(iface, other) == S_OK)
699 {
700 *prefix = iface;
701 IMoniker_AddRef(iface);
702 return MK_S_US;
703 }
704
705 return MonikerCommonPrefixWith(iface, other, prefix);
706}
707
709{
710 TRACE("%p, %p, %p.\n", iface, other, result);
711
712 if (!other || !result)
713 return E_INVALIDARG;
714
715 *result = NULL;
716
717 return MK_E_NOTBINDABLE;
718}
719
720/******************************************************************************
721 * ItemMoniker_GetDisplayName
722 ******************************************************************************/
724 IBindCtx* pbc,
725 IMoniker* pmkToLeft,
726 LPOLESTR *ppszDisplayName)
727{
729 SIZE_T size;
730
731 TRACE("(%p,%p,%p,%p)\n",iface,pbc,pmkToLeft,ppszDisplayName);
732
733 if (ppszDisplayName==NULL)
734 return E_POINTER;
735
736 if (pmkToLeft!=NULL){
737 return E_INVALIDARG;
738 }
739
740 size = lstrlenW(This->itemName) + 1;
741 if (This->itemDelimiter)
742 size += lstrlenW(This->itemDelimiter);
743 size *= sizeof(WCHAR);
744
745 *ppszDisplayName = CoTaskMemAlloc(size);
746 if (*ppszDisplayName==NULL)
747 return E_OUTOFMEMORY;
748
749 (*ppszDisplayName)[0] = 0;
750 if (This->itemDelimiter)
751 lstrcatW(*ppszDisplayName, This->itemDelimiter);
752 lstrcatW(*ppszDisplayName,This->itemName);
753
754 TRACE("-- %s\n", debugstr_w(*ppszDisplayName));
755
756 return S_OK;
757}
758
759/******************************************************************************
760 * ItemMoniker_ParseDisplayName
761 ******************************************************************************/
763 LPOLESTR displayname, ULONG *eaten, IMoniker **ppmkOut)
764{
768 HRESULT hr;
769
770 TRACE("%p, %p, %p, %s, %p, %p.\n", iface, pbc, pmkToLeft, debugstr_w(displayname), eaten, ppmkOut);
771
772 if (!pmkToLeft)
773 return MK_E_SYNTAX;
774
775 hr = IMoniker_BindToObject(pmkToLeft, pbc, NULL, &IID_IOleItemContainer, (void **)&container);
776 if (SUCCEEDED(hr))
777 {
779 {
780 hr = IOleItemContainer_GetObject(container, This->itemName, get_bind_speed_from_bindctx(pbc), pbc,
781 &IID_IParseDisplayName, (void **)&parser);
782 if (SUCCEEDED(hr))
783 {
784 hr = IParseDisplayName_ParseDisplayName(parser, pbc, displayname, eaten, ppmkOut);
785 IParseDisplayName_Release(parser);
786 }
787 }
788 IOleItemContainer_Release(container);
789 }
790
791 return hr;
792}
793
794/******************************************************************************
795 * ItemMoniker_IsSystemMoniker
796 ******************************************************************************/
798{
799 TRACE("(%p,%p)\n",iface,pwdMksys);
800
801 if (!pwdMksys)
802 return E_POINTER;
803
804 (*pwdMksys)=MKSYS_ITEMMONIKER;
805
806 return S_OK;
807}
808
809/*******************************************************************************
810 * ItemMonikerIROTData_QueryInterface
811 *******************************************************************************/
813 void **ppvObject)
814{
815
817
818 TRACE("(%p,%s,%p)\n",iface,debugstr_guid(riid),ppvObject);
819
820 return ItemMonikerImpl_QueryInterface(&This->IMoniker_iface, riid, ppvObject);
821}
822
823/***********************************************************************
824 * ItemMonikerIROTData_AddRef
825 */
827{
829
830 TRACE("(%p)\n",iface);
831
832 return ItemMonikerImpl_AddRef(&This->IMoniker_iface);
833}
834
835/***********************************************************************
836 * ItemMonikerIROTData_Release
837 */
839{
841
842 TRACE("(%p)\n",iface);
843
844 return ItemMonikerImpl_Release(&This->IMoniker_iface);
845}
846
847/******************************************************************************
848 * ItemMonikerIROTData_GetComparisonData
849 ******************************************************************************/
851 ULONG *data_len)
852{
854 int name_len = lstrlenW(This->itemName);
855 int delim_len, i;
856 WCHAR *ptrW;
857
858 TRACE("%p, %p, %lu, %p.\n", iface, buffer, max_len, data_len);
859
860 delim_len = This->itemDelimiter && This->itemDelimiter[0] ? lstrlenW(This->itemDelimiter) : 0;
861 *data_len = sizeof(CLSID) + sizeof(WCHAR) + (delim_len + name_len) * sizeof(WCHAR);
862 if (max_len < *data_len)
863 return E_OUTOFMEMORY;
864
865 /* write CLSID */
866 memcpy(buffer, &CLSID_ItemMoniker, sizeof(CLSID));
867 buffer += sizeof(CLSID);
868
869 /* write delimiter */
870 for (i = 0, ptrW = (WCHAR *)buffer; i < delim_len; ++i)
871 ptrW[i] = towupper(This->itemDelimiter[i]);
872 buffer += (delim_len * sizeof(WCHAR));
873
874 /* write name */
875 for (i = 0, ptrW = (WCHAR *)buffer; i < name_len; ++i)
876 ptrW[i] = towupper(This->itemName[i]);
877 ptrW[i] = 0;
878
879 return S_OK;
880}
881
882/********************************************************************************/
883/* Virtual function table for the ItemMonikerImpl class which include IPersist,*/
884/* IPersistStream and IMoniker functions. */
885static const IMonikerVtbl VT_ItemMonikerImpl =
886 {
910};
911
913{
914 if (iface->lpVtbl != &VT_ItemMonikerImpl)
915 return NULL;
916 return CONTAINING_RECORD(iface, ItemMonikerImpl, IMoniker_iface);
917}
918
919/********************************************************************************/
920/* Virtual function table for the IROTData class. */
921static const IROTDataVtbl VT_ROTDataImpl =
922{
927};
928
929/******************************************************************************
930 * CreateItemMoniker [OLE32.@]
931 ******************************************************************************/
933{
935 int str_len;
936 HRESULT hr;
937
938 TRACE("%s, %s, %p.\n", debugstr_w(delimiter), debugstr_w(name), ret);
939
940 if (!(moniker = calloc(1, sizeof(*moniker))))
941 return E_OUTOFMEMORY;
942
944 moniker->IROTData_iface.lpVtbl = &VT_ROTDataImpl;
945 moniker->ref = 1;
946
947 str_len = (lstrlenW(name) + 1) * sizeof(WCHAR);
948 moniker->itemName = malloc(str_len);
949 if (!moniker->itemName)
950 {
952 goto failed;
953 }
954 memcpy(moniker->itemName, name, str_len);
955
956 if (delimiter)
957 {
958 str_len = (lstrlenW(delimiter) + 1) * sizeof(WCHAR);
959 moniker->itemDelimiter = malloc(str_len);
960 if (!moniker->itemDelimiter)
961 {
963 goto failed;
964 }
965 memcpy(moniker->itemDelimiter, delimiter, str_len);
966 }
967
969
970 return S_OK;
971
972failed:
973 IMoniker_Release(&moniker->IMoniker_iface);
974
975 return hr;
976}
977
979{
981 HRESULT hr;
982
983 TRACE("(%p, %s, %p)\n", outer, debugstr_guid(riid), ppv);
984
985 *ppv = NULL;
986
987 if (outer)
989
990 if (FAILED(hr = CreateItemMoniker(L"", L"", &moniker)))
991 return hr;
992
993 hr = IMoniker_QueryInterface(moniker, riid, ppv);
994 IMoniker_Release(moniker);
995
996 return hr;
997}
GLfloat rot
Definition: 3dtext.c:36
HRESULT create_anti_moniker(DWORD order, IMoniker **ret)
Definition: antimoniker.c:606
BOOL is_anti_moniker(IMoniker *iface, DWORD *order)
Definition: antimoniker.c:54
HRESULT WINAPI CreateAntiMoniker(IMoniker **moniker)
Definition: antimoniker.c:626
#define InterlockedIncrement
Definition: armddk.h:53
#define InterlockedDecrement
Definition: armddk.h:52
#define WINE_DEFAULT_DEBUG_CHANNEL(t)
Definition: precomp.h:23
#define WARN(fmt,...)
Definition: precomp.h:61
const GUID IID_IUnknown
HRESULT WINAPI MonikerCommonPrefixWith(IMoniker *pmkThis, IMoniker *pmkOther, IMoniker **ppmkCommon)
HRESULT WINAPI CreateGenericComposite(IMoniker *left, IMoniker *right, IMoniker **composite)
#define E_OUTOFMEMORY
Definition: ddrawi.h:100
#define E_INVALIDARG
Definition: ddrawi.h:101
#define E_FAIL
Definition: ddrawi.h:102
#define free
Definition: debug_ros.c:5
#define malloc
Definition: debug_ros.c:4
#define NULL
Definition: types.h:112
#define TRUE
Definition: types.h:120
#define FALSE
Definition: types.h:117
#define CP_ACP
Definition: compat.h:109
#define WideCharToMultiByte
Definition: compat.h:111
#define MultiByteToWideChar
Definition: compat.h:110
#define wcsicmp
Definition: compat.h:15
#define lstrlenW
Definition: compat.h:750
HRESULT MonikerMarshal_Create(IMoniker *inner, IUnknown **outer)
Definition: moniker.c:1361
return ret
Definition: mutex.c:146
#define L(x)
Definition: resources.c:13
unsigned int BOOL
Definition: ntddk_ex.h:94
unsigned long DWORD
Definition: ntddk_ex.h:95
GLuint GLuint end
Definition: gl.h:1545
GLuint res
Definition: glext.h:9613
GLuint buffer
Definition: glext.h:5915
GLsizeiptr size
Definition: glext.h:5919
GLdouble GLdouble right
Definition: glext.h:10859
GLuint GLfloat * val
Definition: glext.h:7180
GLuint64EXT * result
Definition: glext.h:11304
GLuint GLdouble GLdouble GLint GLint order
Definition: glext.h:11194
GLenum GLsizei len
Definition: glext.h:6722
GLfloat GLfloat GLfloat GLfloat h
Definition: glext.h:7723
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
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
static HRESULT WINAPI ItemMonikerImpl_ComposeWith(IMoniker *iface, IMoniker *right, BOOL only_if_not_generic, IMoniker **result)
Definition: itemmoniker.c:506
static HRESULT WINAPI ItemMonikerImpl_Enum(IMoniker *iface, BOOL fForward, IEnumMoniker **ppenumMoniker)
Definition: itemmoniker.c:527
static HRESULT WINAPI ItemMonikerImpl_Inverse(IMoniker *iface, IMoniker **ppmk)
Definition: itemmoniker.c:683
static HRESULT WINAPI ItemMonikerROTDataImpl_GetComparisonData(IROTData *iface, BYTE *buffer, ULONG max_len, ULONG *data_len)
Definition: itemmoniker.c:850
static ULONG WINAPI ItemMonikerROTDataImpl_Release(IROTData *iface)
Definition: itemmoniker.c:838
static HRESULT WINAPI ItemMonikerImpl_GetSizeMax(IMoniker *iface, ULARGE_INTEGER *pcbSize)
Definition: itemmoniker.c:388
static HRESULT WINAPI ItemMonikerImpl_Save(IMoniker *iface, IStream *stream, BOOL fClearDirty)
Definition: itemmoniker.c:345
static HRESULT WINAPI ItemMonikerImpl_BindToStorage(IMoniker *iface, IBindCtx *pbc, IMoniker *pmkToLeft, REFIID riid, void **ppvResult)
Definition: itemmoniker.c:464
static HRESULT item_moniker_load_string_record(IStream *stream, WCHAR **ret)
Definition: itemmoniker.c:240
static const IUnknownVtbl container_lock_vtbl
Definition: itemmoniker.c:106
static HRESULT WINAPI ItemMonikerImpl_Reduce(IMoniker *iface, IBindCtx *pbc, DWORD dwReduceHowFar, IMoniker **ppmkToLeft, IMoniker **ppmkReduced)
Definition: itemmoniker.c:491
static HRESULT WINAPI ItemMonikerImpl_GetDisplayName(IMoniker *iface, IBindCtx *pbc, IMoniker *pmkToLeft, LPOLESTR *ppszDisplayName)
Definition: itemmoniker.c:723
HRESULT WINAPI CreateItemMoniker(const WCHAR *delimiter, const WCHAR *name, IMoniker **ret)
Definition: itemmoniker.c:932
static HRESULT WINAPI ItemMonikerImpl_IsDirty(IMoniker *iface)
Definition: itemmoniker.c:229
static HRESULT WINAPI ItemMonikerImpl_IsRunning(IMoniker *iface, IBindCtx *pbc, IMoniker *pmkToLeft, IMoniker *pmkNewlyRunning)
Definition: itemmoniker.c:586
static DWORD get_bind_speed_from_bindctx(IBindCtx *pbc)
Definition: itemmoniker.c:412
static HRESULT WINAPI ItemMonikerImpl_Hash(IMoniker *iface, DWORD *pdwHash)
Definition: itemmoniker.c:561
static HRESULT WINAPI container_lock_QueryInterface(IUnknown *iface, REFIID riid, void **obj)
Definition: itemmoniker.c:71
static HRESULT WINAPI ItemMonikerImpl_BindToObject(IMoniker *iface, IBindCtx *pbc, IMoniker *pmkToLeft, REFIID riid, VOID **ppvResult)
Definition: itemmoniker.c:427
static const IROTDataVtbl VT_ROTDataImpl
Definition: itemmoniker.c:921
static HRESULT WINAPI ItemMonikerImpl_GetTimeOfLastChange(IMoniker *iface, IBindCtx *pbc, IMoniker *pmkToLeft, FILETIME *pItemTime)
Definition: itemmoniker.c:636
static ULONG WINAPI container_lock_Release(IUnknown *iface)
Definition: itemmoniker.c:91
static ItemMonikerImpl * impl_from_IROTData(IROTData *iface)
Definition: itemmoniker.c:54
static struct container_lock * impl_lock_from_IUnknown(IUnknown *iface)
Definition: itemmoniker.c:66
static ULONG WINAPI ItemMonikerImpl_Release(IMoniker *iface)
Definition: itemmoniker.c:193
static ItemMonikerImpl * impl_from_IMoniker(IMoniker *iface)
Definition: itemmoniker.c:47
static HRESULT WINAPI ItemMonikerImpl_CommonPrefixWith(IMoniker *iface, IMoniker *other, IMoniker **prefix)
Definition: itemmoniker.c:693
static ItemMonikerImpl * unsafe_impl_from_IMoniker(IMoniker *iface)
Definition: itemmoniker.c:912
static const IMonikerVtbl VT_ItemMonikerImpl
Definition: itemmoniker.c:885
static HRESULT set_container_lock(IOleItemContainer *container, IBindCtx *pbc)
Definition: itemmoniker.c:113
static HRESULT WINAPI ItemMonikerImpl_RelativePathTo(IMoniker *iface, IMoniker *other, IMoniker **result)
Definition: itemmoniker.c:708
HRESULT WINAPI ItemMoniker_CreateInstance(IClassFactory *iface, IUnknown *outer, REFIID riid, void **ppv)
Definition: itemmoniker.c:978
static HRESULT WINAPI ItemMonikerImpl_IsEqual(IMoniker *iface, IMoniker *other)
Definition: itemmoniker.c:542
static HRESULT WINAPI ItemMonikerImpl_GetClassID(IMoniker *iface, CLSID *pClassID)
Definition: itemmoniker.c:214
static HRESULT WINAPI ItemMonikerImpl_ParseDisplayName(IMoniker *iface, IBindCtx *pbc, IMoniker *pmkToLeft, LPOLESTR displayname, ULONG *eaten, IMoniker **ppmkOut)
Definition: itemmoniker.c:762
static HRESULT WINAPI ItemMonikerImpl_IsSystemMoniker(IMoniker *iface, DWORD *pwdMksys)
Definition: itemmoniker.c:797
static ULONG WINAPI container_lock_AddRef(IUnknown *iface)
Definition: itemmoniker.c:85
static HRESULT WINAPI ItemMonikerImpl_Load(IMoniker *iface, IStream *stream)
Definition: itemmoniker.c:323
static HRESULT WINAPI ItemMonikerImpl_QueryInterface(IMoniker *iface, REFIID riid, void **ppvObject)
Definition: itemmoniker.c:140
static ULONG WINAPI ItemMonikerROTDataImpl_AddRef(IROTData *iface)
Definition: itemmoniker.c:826
static ULONG WINAPI ItemMonikerImpl_AddRef(IMoniker *iface)
Definition: itemmoniker.c:181
static HRESULT WINAPI ItemMonikerROTDataImpl_QueryInterface(IROTData *iface, REFIID riid, void **ppvObject)
Definition: itemmoniker.c:812
#define debugstr_guid
Definition: kernel32.h:35
#define debugstr_w
Definition: kernel32.h:32
LPWSTR WINAPI lstrcatW(LPWSTR lpString1, LPCWSTR lpString2)
Definition: lstring.c:274
void *WINAPI CoTaskMemAlloc(SIZE_T size)
Definition: malloc.c:381
#define memcpy(s1, s2, n)
Definition: mkisofs.h:878
const char * delimiter
Definition: string.c:1779
static IUnknown * outer
Definition: compobj.c:82
static BSTR *static LPOLESTR
Definition: varformat.c:44
int other
Definition: msacm.c:1376
IID CLSID
Definition: mstsclib_i.c:62
#define DWORD
Definition: nt_native.h:44
const GUID IID_IParseDisplayName
const GUID IID_IOleItemContainer
long LONG
Definition: pedump.c:60
const GUID IID_IPersist
Definition: proxy.cpp:14
const GUID IID_IPersistStream
Definition: proxy.cpp:13
#define IsEqualGUID(rguid1, rguid2)
Definition: guiddef.h:147
#define IsEqualIID(riid1, riid2)
Definition: guiddef.h:95
#define REFIID
Definition: guiddef.h:118
#define calloc
Definition: rosglue.h:14
const WCHAR * str
#define towupper(c)
Definition: wctype.h:99
HRESULT hr
Definition: shlfolder.c:183
#define TRACE(s)
Definition: solgame.cpp:4
LPOLESTR itemDelimiter
Definition: itemmoniker.c:43
IROTData IROTData_iface
Definition: itemmoniker.c:40
IMoniker IMoniker_iface
Definition: itemmoniker.c:39
IUnknown * pMarshal
Definition: itemmoniker.c:44
LPOLESTR itemName
Definition: itemmoniker.c:42
struct _ULARGE_INTEGER::@4426 u
IUnknown IUnknown_iface
Definition: itemmoniker.c:61
IOleItemContainer * container
Definition: itemmoniker.c:63
Definition: main.c:40
IMoniker IMoniker_iface
Definition: main.c:41
Definition: name.c:39
Definition: import.c:81
Definition: parse.h:23
rwlock_t lock
Definition: tcpcore.h:0
Character const *const prefix
Definition: tempnam.cpp:195
#define str_len
Definition: treelist.c:89
ULONG_PTR SIZE_T
Definition: typedefs.h:80
#define CONTAINING_RECORD(address, type, field)
Definition: typedefs.h:260
uint32_t ULONG
Definition: typedefs.h:59
#define WINAPI
Definition: msvc.h:6
#define S_FALSE
Definition: winerror.h:3451
#define MK_S_REDUCED_TO_SELF
Definition: winerror.h:3892
#define E_NOINTERFACE
Definition: winerror.h:3479
#define MK_E_NOTBINDABLE
Definition: winerror.h:3903
#define MK_E_SYNTAX
Definition: winerror.h:3896
#define CLASS_E_NOAGGREGATION
Definition: winerror.h:3771
#define MK_E_NEEDGENERIC
Definition: winerror.h:3893
#define E_POINTER
Definition: winerror.h:3480
#define MK_S_US
Definition: winerror.h:3899
__wchar_t WCHAR
Definition: xmlstorage.h:180
unsigned char BYTE
Definition: xxhash.c:193