2 * ITSS Moniker implementation
4 * Copyright 2004 Mike McCormack
6 * Implementation of the infamous mk:@MSITStore moniker
8 * This library is free software; you can redistribute it and/or
9 * modify it under the terms of the GNU Lesser General Public
10 * License as published by the Free Software Foundation; either
11 * version 2.1 of the License, or (at your option) any later version.
13 * This library is distributed in the hope that it will be useful,
14 * but WITHOUT ANY WARRANTY; without even the implied warranty of
15 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
16 * Lesser General Public License for more details.
18 * You should have received a copy of the GNU Lesser General Public
19 * License along with this library; if not, write to the Free Software
20 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
40 #include "wine/unicode.h"
41 #include "wine/debug.h"
45 WINE_DEFAULT_DEBUG_CHANNEL(itss
);
47 /*****************************************************************************/
50 IMonikerVtbl
*vtbl_ITS_IMoniker
;
56 /*** IUnknown methods ***/
57 static HRESULT WINAPI
ITS_IMonikerImpl_QueryInterface(
62 ITS_IMonikerImpl
*This
= (ITS_IMonikerImpl
*)iface
;
64 if (IsEqualGUID(riid
, &IID_IUnknown
)
65 || IsEqualGUID(riid
, &IID_IParseDisplayName
))
67 IClassFactory_AddRef(iface
);
72 WARN("(%p)->(%s,%p),not found\n",This
,debugstr_guid(riid
),ppvObject
);
76 static ULONG WINAPI
ITS_IMonikerImpl_AddRef(
79 ITS_IMonikerImpl
*This
= (ITS_IMonikerImpl
*)iface
;
84 static ULONG WINAPI
ITS_IMonikerImpl_Release(
87 ITS_IMonikerImpl
*This
= (ITS_IMonikerImpl
*)iface
;
88 ULONG ref
= --This
->ref
;
91 HeapFree(GetProcessHeap(), 0, This
);
96 /*** IPersist methods ***/
97 static HRESULT WINAPI
ITS_IMonikerImpl_GetClassID(
101 ITS_IMonikerImpl
*This
= (ITS_IMonikerImpl
*)iface
;
103 TRACE("%p %p\n", This
, pClassID
);
104 memcpy( pClassID
, &CLSID_ITStorage
, sizeof (CLSID
) );
108 /*** IPersistStream methods ***/
109 static HRESULT WINAPI
ITS_IMonikerImpl_IsDirty(
116 static HRESULT WINAPI
ITS_IMonikerImpl_Load(
124 static HRESULT WINAPI
ITS_IMonikerImpl_Save(
133 static HRESULT WINAPI
ITS_IMonikerImpl_GetSizeMax(
135 ULARGE_INTEGER
* pcbSize
)
141 /*** IMoniker methods ***/
142 static HRESULT WINAPI
ITS_IMonikerImpl_BindToObject(
153 static HRESULT WINAPI
ITS_IMonikerImpl_BindToStorage(
160 ITS_IMonikerImpl
*This
= (ITS_IMonikerImpl
*)iface
;
161 DWORD grfMode
= STGM_SIMPLE
| STGM_READ
| STGM_SHARE_EXCLUSIVE
;
163 IStorage
*stg
= NULL
;
165 TRACE("%p %p %p %s %p\n", This
,
166 pbc
, pmkToLeft
, debugstr_guid(riid
), ppvObj
);
168 r
= ITSS_StgOpenStorage( This
->szFile
, NULL
, grfMode
, 0, 0, &stg
);
171 TRACE("Opened storage %s\n", debugstr_w( This
->szFile
) );
172 if (IsEqualGUID(riid
, &IID_IStream
))
173 r
= IStorage_OpenStream( stg
, This
->szHtml
,
174 NULL
, grfMode
, 0, (IStream
**)ppvObj
);
175 else if (IsEqualGUID(riid
, &IID_IStorage
))
176 r
= IStorage_OpenStorage( stg
, This
->szHtml
,
177 NULL
, grfMode
, NULL
, 0, (IStorage
**)ppvObj
);
179 r
= STG_E_ACCESSDENIED
;
180 IStorage_Release( stg
);
186 static HRESULT WINAPI
ITS_IMonikerImpl_Reduce(
189 DWORD dwReduceHowFar
,
190 IMoniker
** ppmkToLeft
,
191 IMoniker
** ppmkReduced
)
197 static HRESULT WINAPI
ITS_IMonikerImpl_ComposeWith(
200 BOOL fOnlyIfNotGeneric
,
201 IMoniker
** ppmkComposite
)
207 static HRESULT WINAPI
ITS_IMonikerImpl_Enum(
210 IEnumMoniker
** ppenumMoniker
)
216 static HRESULT WINAPI
ITS_IMonikerImpl_IsEqual(
218 IMoniker
* pmkOtherMoniker
)
224 static HRESULT WINAPI
ITS_IMonikerImpl_Hash(
232 static HRESULT WINAPI
ITS_IMonikerImpl_IsRunning(
236 IMoniker
* pmkNewlyRunning
)
242 static HRESULT WINAPI
ITS_IMonikerImpl_GetTimeOfLastChange(
252 static HRESULT WINAPI
ITS_IMonikerImpl_Inverse(
260 static HRESULT WINAPI
ITS_IMonikerImpl_CommonPrefixWith(
263 IMoniker
** ppmkPrefix
)
269 static HRESULT WINAPI
ITS_IMonikerImpl_RelativePathTo(
272 IMoniker
** ppmkRelPath
)
278 static HRESULT WINAPI
ITS_IMonikerImpl_GetDisplayName(
282 LPOLESTR
* ppszDisplayName
)
284 ITS_IMonikerImpl
*This
= (ITS_IMonikerImpl
*)iface
;
285 static const WCHAR szFormat
[] = {
286 'm','s','-','i','t','s',':','%','s',':',':','%','s',0 };
287 DWORD len
= sizeof szFormat
/ sizeof(WCHAR
);
290 TRACE("%p %p %p %p\n", iface
, pbc
, pmkToLeft
, ppszDisplayName
);
292 len
= strlenW( This
->szFile
) + strlenW( This
->szHtml
);
293 str
= CoTaskMemAlloc( len
*sizeof(WCHAR
) );
294 sprintfW( str
, szFormat
, This
->szFile
, This
->szHtml
);
296 *ppszDisplayName
= str
;
301 static HRESULT WINAPI
ITS_IMonikerImpl_ParseDisplayName(
305 LPOLESTR pszDisplayName
,
313 static HRESULT WINAPI
ITS_IMonikerImpl_IsSystemMoniker(
321 static IMonikerVtbl ITS_IMonikerImpl_Vtbl
=
323 ITS_IMonikerImpl_QueryInterface
,
324 ITS_IMonikerImpl_AddRef
,
325 ITS_IMonikerImpl_Release
,
326 ITS_IMonikerImpl_GetClassID
,
327 ITS_IMonikerImpl_IsDirty
,
328 ITS_IMonikerImpl_Load
,
329 ITS_IMonikerImpl_Save
,
330 ITS_IMonikerImpl_GetSizeMax
,
331 ITS_IMonikerImpl_BindToObject
,
332 ITS_IMonikerImpl_BindToStorage
,
333 ITS_IMonikerImpl_Reduce
,
334 ITS_IMonikerImpl_ComposeWith
,
335 ITS_IMonikerImpl_Enum
,
336 ITS_IMonikerImpl_IsEqual
,
337 ITS_IMonikerImpl_Hash
,
338 ITS_IMonikerImpl_IsRunning
,
339 ITS_IMonikerImpl_GetTimeOfLastChange
,
340 ITS_IMonikerImpl_Inverse
,
341 ITS_IMonikerImpl_CommonPrefixWith
,
342 ITS_IMonikerImpl_RelativePathTo
,
343 ITS_IMonikerImpl_GetDisplayName
,
344 ITS_IMonikerImpl_ParseDisplayName
,
345 ITS_IMonikerImpl_IsSystemMoniker
348 static HRESULT
ITS_IMoniker_create( IMoniker
**ppObj
, LPWSTR name
, DWORD n
)
350 ITS_IMonikerImpl
*itsmon
;
353 /* szFile[1] has space for one character already */
354 sz
= sizeof(ITS_IMonikerImpl
) + strlenW( name
)*sizeof(WCHAR
);
356 itsmon
= HeapAlloc( GetProcessHeap(), 0, sz
);
357 itsmon
->vtbl_ITS_IMoniker
= &ITS_IMonikerImpl_Vtbl
;
359 strcpyW( itsmon
->szFile
, name
);
360 itsmon
->szHtml
= &itsmon
->szFile
[n
];
362 while( *itsmon
->szHtml
== ':' )
363 *itsmon
->szHtml
++ = 0;
365 TRACE("-> %p %s %s\n", itsmon
,
366 debugstr_w(itsmon
->szFile
), debugstr_w(itsmon
->szHtml
) );
367 *ppObj
= (IMoniker
*) itsmon
;
372 /*****************************************************************************/
375 IParseDisplayNameVtbl
*vtbl_ITS_IParseDisplayName
;
377 } ITS_IParseDisplayNameImpl
;
379 static HRESULT WINAPI
ITS_IParseDisplayNameImpl_QueryInterface(
380 IParseDisplayName
* iface
,
384 ITS_IParseDisplayNameImpl
*This
= (ITS_IParseDisplayNameImpl
*)iface
;
386 if (IsEqualGUID(riid
, &IID_IUnknown
)
387 || IsEqualGUID(riid
, &IID_IParseDisplayName
))
389 IClassFactory_AddRef(iface
);
394 WARN("(%p)->(%s,%p),not found\n",This
,debugstr_guid(riid
),ppvObject
);
395 return E_NOINTERFACE
;
398 static ULONG WINAPI
ITS_IParseDisplayNameImpl_AddRef(
399 IParseDisplayName
* iface
)
401 ITS_IParseDisplayNameImpl
*This
= (ITS_IParseDisplayNameImpl
*)iface
;
403 return ++(This
->ref
);
406 static ULONG WINAPI
ITS_IParseDisplayNameImpl_Release(
407 IParseDisplayName
* iface
)
409 ITS_IParseDisplayNameImpl
*This
= (ITS_IParseDisplayNameImpl
*)iface
;
410 ULONG ref
= --This
->ref
;
413 HeapFree(GetProcessHeap(), 0, This
);
418 static HRESULT WINAPI
ITS_IParseDisplayNameImpl_ParseDisplayName(
419 IParseDisplayName
*iface
,
421 LPOLESTR pszDisplayName
,
425 static const WCHAR szPrefix
[] = {
426 '@','M','S','I','T','S','t','o','r','e',':',0 };
427 const DWORD prefix_len
= (sizeof szPrefix
/sizeof szPrefix
[0])-1;
430 ITS_IParseDisplayNameImpl
*This
= (ITS_IParseDisplayNameImpl
*)iface
;
432 TRACE("%p %s %p %p\n", This
,
433 debugstr_w( pszDisplayName
), pchEaten
, ppmkOut
);
435 if( strncmpW( pszDisplayName
, szPrefix
, prefix_len
) )
438 /* search backwards for a double colon */
439 for( n
= strlenW( pszDisplayName
) - 3; prefix_len
<= n
; n
-- )
440 if( ( pszDisplayName
[n
] == ':' ) && ( pszDisplayName
[n
+1] == ':' ) )
446 if( !pszDisplayName
[n
+2] )
449 *pchEaten
= strlenW( pszDisplayName
) - n
- 3;
451 return ITS_IMoniker_create( ppmkOut
,
452 &pszDisplayName
[prefix_len
], n
-prefix_len
);
455 static IParseDisplayNameVtbl ITS_IParseDisplayNameImpl_Vtbl
=
457 ITS_IParseDisplayNameImpl_QueryInterface
,
458 ITS_IParseDisplayNameImpl_AddRef
,
459 ITS_IParseDisplayNameImpl_Release
,
460 ITS_IParseDisplayNameImpl_ParseDisplayName
463 HRESULT
ITS_IParseDisplayName_create(IUnknown
*pUnkOuter
, LPVOID
*ppObj
)
465 ITS_IParseDisplayNameImpl
*its
;
467 its
= HeapAlloc( GetProcessHeap(), 0, sizeof(ITS_IParseDisplayNameImpl
) );
468 its
->vtbl_ITS_IParseDisplayName
= &ITS_IParseDisplayNameImpl_Vtbl
;
471 TRACE("-> %p\n", its
);
472 *ppObj
= (LPVOID
) its
;