Sweden-Number/dlls/ole32/moniker.c

1220 lines
36 KiB
C
Raw Normal View History

Release 980315 Sun Mar 15 03:46:50 1998 Dimitrie O. Paun <dimi@mail.cs.toronto.edu> * [*/*] Fixed some dprintf_ such that there is one and only one new line for each dprintf and that new line occurs at the end. Transformed some fprintfs into proper debug statements. Removed much redundancy from most of the debug statements. The redundancy appeared because now the component and function name is output automatically. Most debug statements also used to output the name of the function. All these changes prepared the source to switch completely to the new debugging interface. For more info, refer to ./documentation/debug-msg Sat Mar 14 19:45:23 1997 Andreas Mohr <100.30936@germany.net> * [misc/shell.c] [if1632/kernel.spec] Changed parameters of FUNC004() to fix a crash. Not sure if this fix is correct (doc wanted). * [windows/user.c] [if1632/user.spec] [include/user.h] Implemented UserSeeUserDo. * [msdos/int21.c] [include/msdos.h] Added "GET LIST OF LISTS" (INT 21/52h). Sat Mar 14 15:48:02 1998 Douglas Ridgway <ridgway@gmcl.com> * [include/windows.h] [relay32/gdi32.spec] [objects/enhmetafile.c] Beginnings of enhanced metafile support. Fri Mar 13 20:53:09 1998 John Richardson <jrichard@zko.dec.com> * [win32/console.c] Restart interrupted console writes. Fri Mar 13 18:59:24 1998 Matthew Becker <mbecker@glasscity.net> * [*/*.c] Updated documentation for API manpages. * [windows/dce.c] ReleaseDC16: Fixed cast. * [include/windows.h] [memory/virtual.c] VirtualQuery{Ex} should return DWORD instead of BOOL32. Fri Mar 13 13:03:06 1998 Marcus Meissner <msmeissn@cip.informatik.uni-erlangen.de> * [README][documentation/status/] README updated, added lzexpand,version and multimedia status notes to new documentation/status directory. * [ole/*.c][if1632/typelib.spec] Added typelib stubs, several small additions and fixes. * [loader/pe_image.c] Fixed a small bug (fixup_imports got passed the wrong hModule in a remapcase). * [loader/signal.c][if1632/signal.c][misc/winsock_dns.c] [loader/module.c] Fixed some recursive debugger crashes (caused by invalid FS). * [misc/registry.c] Two bugs fixed. Fri Mar 13 04:55:01 1998 David Lee Lambert <lamber45@egr.msu.edu> * [include/winnt.h] [include/winnls.h] Moved LANG_xxx flags to winnls.h * [include/winnls.h] Added flags for GetDateFormat(); fixed validity of LOCALE_SYSTEM_DEFAULT. * [include/windows.h] Added GetTimeFormat() prototypes. * [ole/ole2nls.c] Implemented ASCII date- and time-functions, using an optimized common core; added stubs for Unicode versions; started work on a Unicode core. * [AUTHORS] Added my name. Mon Mar 9 20:10:15 1998 Eric Kohl <ekohl@abo.rhein-zeitung.de> * [relay32/comctl32.spec] [include/imagelist.h] [include/commctrl.h] [misc/imagelist.c] [misc/Makefile.in] First attempt at implementing ImageLists. Sun Mar 8 20:19:49 1998 Uwe Bonnes <bon@elektron.ikp.physik.tu-darmstadt.de> * [files/dos_fs.c] [configure.in] Try to get FileTimeToLocalFileTime,FileTimeToSystemTime and SystemTimeToFileTime right. Use timegm() where available. * [misc/lstr.c] Fix an off by one error in FormatMessage and handle the case when args = NULL (used by programs to get the length of the string). * [win32/console.c] Actual display a per-process Title string, better working attempt for WriteConsole32W and ReadConsole32W. Fri Mar 6 20:33:45 1998 Slaven Rezic <eserte@cs.tu-berlin.de> * [include/config.h.in][configure.in][multimedia/audio.c] [multimedia/dsound.c] Added check for FreeBSD sound system. Sun Mar 1 17:40:10 1998 Jason Schonberg <schon@mti.sgi.com> * [controls/edit.c] [include/ole.h] [include/shlobj.h] Removed final commas in enum types. Mon Feb 23 07:52:18 1998 Luiz Otavio L. Zorzella <zorzella@nr.conexware.com> * [multimedia/time.c] Workaround to avoid infinite recursion inside timeGetTime. * [multimedia/audio.c] WODM_GETNUMDEVS and WIDM_GETNUMDEVS only return 1 now if the SOUND_DEV can be opened, or if it's busy.
1998-03-15 21:29:56 +01:00
/*
* Monikers
*
* Copyright 1998 Marcus Meissner
* Copyright 1999 Noomen Hamza
* Copyright 2005 Robert Shearman (for CodeWeavers)
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
* License as published by the Free Software Foundation; either
* version 2.1 of the License, or (at your option) any later version.
*
* This library is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public
* License along with this library; if not, write to the Free Software
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
*
* TODO:
* - IRunningObjectTable should work interprocess, but currently doesn't.
* Native (on Win2k at least) uses an undocumented RPC interface, IROT, to
* communicate with RPCSS which contains the table of marshalled data.
Release 980315 Sun Mar 15 03:46:50 1998 Dimitrie O. Paun <dimi@mail.cs.toronto.edu> * [*/*] Fixed some dprintf_ such that there is one and only one new line for each dprintf and that new line occurs at the end. Transformed some fprintfs into proper debug statements. Removed much redundancy from most of the debug statements. The redundancy appeared because now the component and function name is output automatically. Most debug statements also used to output the name of the function. All these changes prepared the source to switch completely to the new debugging interface. For more info, refer to ./documentation/debug-msg Sat Mar 14 19:45:23 1997 Andreas Mohr <100.30936@germany.net> * [misc/shell.c] [if1632/kernel.spec] Changed parameters of FUNC004() to fix a crash. Not sure if this fix is correct (doc wanted). * [windows/user.c] [if1632/user.spec] [include/user.h] Implemented UserSeeUserDo. * [msdos/int21.c] [include/msdos.h] Added "GET LIST OF LISTS" (INT 21/52h). Sat Mar 14 15:48:02 1998 Douglas Ridgway <ridgway@gmcl.com> * [include/windows.h] [relay32/gdi32.spec] [objects/enhmetafile.c] Beginnings of enhanced metafile support. Fri Mar 13 20:53:09 1998 John Richardson <jrichard@zko.dec.com> * [win32/console.c] Restart interrupted console writes. Fri Mar 13 18:59:24 1998 Matthew Becker <mbecker@glasscity.net> * [*/*.c] Updated documentation for API manpages. * [windows/dce.c] ReleaseDC16: Fixed cast. * [include/windows.h] [memory/virtual.c] VirtualQuery{Ex} should return DWORD instead of BOOL32. Fri Mar 13 13:03:06 1998 Marcus Meissner <msmeissn@cip.informatik.uni-erlangen.de> * [README][documentation/status/] README updated, added lzexpand,version and multimedia status notes to new documentation/status directory. * [ole/*.c][if1632/typelib.spec] Added typelib stubs, several small additions and fixes. * [loader/pe_image.c] Fixed a small bug (fixup_imports got passed the wrong hModule in a remapcase). * [loader/signal.c][if1632/signal.c][misc/winsock_dns.c] [loader/module.c] Fixed some recursive debugger crashes (caused by invalid FS). * [misc/registry.c] Two bugs fixed. Fri Mar 13 04:55:01 1998 David Lee Lambert <lamber45@egr.msu.edu> * [include/winnt.h] [include/winnls.h] Moved LANG_xxx flags to winnls.h * [include/winnls.h] Added flags for GetDateFormat(); fixed validity of LOCALE_SYSTEM_DEFAULT. * [include/windows.h] Added GetTimeFormat() prototypes. * [ole/ole2nls.c] Implemented ASCII date- and time-functions, using an optimized common core; added stubs for Unicode versions; started work on a Unicode core. * [AUTHORS] Added my name. Mon Mar 9 20:10:15 1998 Eric Kohl <ekohl@abo.rhein-zeitung.de> * [relay32/comctl32.spec] [include/imagelist.h] [include/commctrl.h] [misc/imagelist.c] [misc/Makefile.in] First attempt at implementing ImageLists. Sun Mar 8 20:19:49 1998 Uwe Bonnes <bon@elektron.ikp.physik.tu-darmstadt.de> * [files/dos_fs.c] [configure.in] Try to get FileTimeToLocalFileTime,FileTimeToSystemTime and SystemTimeToFileTime right. Use timegm() where available. * [misc/lstr.c] Fix an off by one error in FormatMessage and handle the case when args = NULL (used by programs to get the length of the string). * [win32/console.c] Actual display a per-process Title string, better working attempt for WriteConsole32W and ReadConsole32W. Fri Mar 6 20:33:45 1998 Slaven Rezic <eserte@cs.tu-berlin.de> * [include/config.h.in][configure.in][multimedia/audio.c] [multimedia/dsound.c] Added check for FreeBSD sound system. Sun Mar 1 17:40:10 1998 Jason Schonberg <schon@mti.sgi.com> * [controls/edit.c] [include/ole.h] [include/shlobj.h] Removed final commas in enum types. Mon Feb 23 07:52:18 1998 Luiz Otavio L. Zorzella <zorzella@nr.conexware.com> * [multimedia/time.c] Workaround to avoid infinite recursion inside timeGetTime. * [multimedia/audio.c] WODM_GETNUMDEVS and WIDM_GETNUMDEVS only return 1 now if the SOUND_DEV can be opened, or if it's busy.
1998-03-15 21:29:56 +01:00
*/
#include <assert.h>
#include <stdarg.h>
#include <string.h>
#define COBJMACROS
Release 980315 Sun Mar 15 03:46:50 1998 Dimitrie O. Paun <dimi@mail.cs.toronto.edu> * [*/*] Fixed some dprintf_ such that there is one and only one new line for each dprintf and that new line occurs at the end. Transformed some fprintfs into proper debug statements. Removed much redundancy from most of the debug statements. The redundancy appeared because now the component and function name is output automatically. Most debug statements also used to output the name of the function. All these changes prepared the source to switch completely to the new debugging interface. For more info, refer to ./documentation/debug-msg Sat Mar 14 19:45:23 1997 Andreas Mohr <100.30936@germany.net> * [misc/shell.c] [if1632/kernel.spec] Changed parameters of FUNC004() to fix a crash. Not sure if this fix is correct (doc wanted). * [windows/user.c] [if1632/user.spec] [include/user.h] Implemented UserSeeUserDo. * [msdos/int21.c] [include/msdos.h] Added "GET LIST OF LISTS" (INT 21/52h). Sat Mar 14 15:48:02 1998 Douglas Ridgway <ridgway@gmcl.com> * [include/windows.h] [relay32/gdi32.spec] [objects/enhmetafile.c] Beginnings of enhanced metafile support. Fri Mar 13 20:53:09 1998 John Richardson <jrichard@zko.dec.com> * [win32/console.c] Restart interrupted console writes. Fri Mar 13 18:59:24 1998 Matthew Becker <mbecker@glasscity.net> * [*/*.c] Updated documentation for API manpages. * [windows/dce.c] ReleaseDC16: Fixed cast. * [include/windows.h] [memory/virtual.c] VirtualQuery{Ex} should return DWORD instead of BOOL32. Fri Mar 13 13:03:06 1998 Marcus Meissner <msmeissn@cip.informatik.uni-erlangen.de> * [README][documentation/status/] README updated, added lzexpand,version and multimedia status notes to new documentation/status directory. * [ole/*.c][if1632/typelib.spec] Added typelib stubs, several small additions and fixes. * [loader/pe_image.c] Fixed a small bug (fixup_imports got passed the wrong hModule in a remapcase). * [loader/signal.c][if1632/signal.c][misc/winsock_dns.c] [loader/module.c] Fixed some recursive debugger crashes (caused by invalid FS). * [misc/registry.c] Two bugs fixed. Fri Mar 13 04:55:01 1998 David Lee Lambert <lamber45@egr.msu.edu> * [include/winnt.h] [include/winnls.h] Moved LANG_xxx flags to winnls.h * [include/winnls.h] Added flags for GetDateFormat(); fixed validity of LOCALE_SYSTEM_DEFAULT. * [include/windows.h] Added GetTimeFormat() prototypes. * [ole/ole2nls.c] Implemented ASCII date- and time-functions, using an optimized common core; added stubs for Unicode versions; started work on a Unicode core. * [AUTHORS] Added my name. Mon Mar 9 20:10:15 1998 Eric Kohl <ekohl@abo.rhein-zeitung.de> * [relay32/comctl32.spec] [include/imagelist.h] [include/commctrl.h] [misc/imagelist.c] [misc/Makefile.in] First attempt at implementing ImageLists. Sun Mar 8 20:19:49 1998 Uwe Bonnes <bon@elektron.ikp.physik.tu-darmstadt.de> * [files/dos_fs.c] [configure.in] Try to get FileTimeToLocalFileTime,FileTimeToSystemTime and SystemTimeToFileTime right. Use timegm() where available. * [misc/lstr.c] Fix an off by one error in FormatMessage and handle the case when args = NULL (used by programs to get the length of the string). * [win32/console.c] Actual display a per-process Title string, better working attempt for WriteConsole32W and ReadConsole32W. Fri Mar 6 20:33:45 1998 Slaven Rezic <eserte@cs.tu-berlin.de> * [include/config.h.in][configure.in][multimedia/audio.c] [multimedia/dsound.c] Added check for FreeBSD sound system. Sun Mar 1 17:40:10 1998 Jason Schonberg <schon@mti.sgi.com> * [controls/edit.c] [include/ole.h] [include/shlobj.h] Removed final commas in enum types. Mon Feb 23 07:52:18 1998 Luiz Otavio L. Zorzella <zorzella@nr.conexware.com> * [multimedia/time.c] Workaround to avoid infinite recursion inside timeGetTime. * [multimedia/audio.c] WODM_GETNUMDEVS and WIDM_GETNUMDEVS only return 1 now if the SOUND_DEV can be opened, or if it's busy.
1998-03-15 21:29:56 +01:00
#include "winerror.h"
#include "windef.h"
#include "winbase.h"
#include "winuser.h"
#include "wtypes.h"
2000-03-08 19:25:22 +01:00
#include "ole2.h"
Release 980315 Sun Mar 15 03:46:50 1998 Dimitrie O. Paun <dimi@mail.cs.toronto.edu> * [*/*] Fixed some dprintf_ such that there is one and only one new line for each dprintf and that new line occurs at the end. Transformed some fprintfs into proper debug statements. Removed much redundancy from most of the debug statements. The redundancy appeared because now the component and function name is output automatically. Most debug statements also used to output the name of the function. All these changes prepared the source to switch completely to the new debugging interface. For more info, refer to ./documentation/debug-msg Sat Mar 14 19:45:23 1997 Andreas Mohr <100.30936@germany.net> * [misc/shell.c] [if1632/kernel.spec] Changed parameters of FUNC004() to fix a crash. Not sure if this fix is correct (doc wanted). * [windows/user.c] [if1632/user.spec] [include/user.h] Implemented UserSeeUserDo. * [msdos/int21.c] [include/msdos.h] Added "GET LIST OF LISTS" (INT 21/52h). Sat Mar 14 15:48:02 1998 Douglas Ridgway <ridgway@gmcl.com> * [include/windows.h] [relay32/gdi32.spec] [objects/enhmetafile.c] Beginnings of enhanced metafile support. Fri Mar 13 20:53:09 1998 John Richardson <jrichard@zko.dec.com> * [win32/console.c] Restart interrupted console writes. Fri Mar 13 18:59:24 1998 Matthew Becker <mbecker@glasscity.net> * [*/*.c] Updated documentation for API manpages. * [windows/dce.c] ReleaseDC16: Fixed cast. * [include/windows.h] [memory/virtual.c] VirtualQuery{Ex} should return DWORD instead of BOOL32. Fri Mar 13 13:03:06 1998 Marcus Meissner <msmeissn@cip.informatik.uni-erlangen.de> * [README][documentation/status/] README updated, added lzexpand,version and multimedia status notes to new documentation/status directory. * [ole/*.c][if1632/typelib.spec] Added typelib stubs, several small additions and fixes. * [loader/pe_image.c] Fixed a small bug (fixup_imports got passed the wrong hModule in a remapcase). * [loader/signal.c][if1632/signal.c][misc/winsock_dns.c] [loader/module.c] Fixed some recursive debugger crashes (caused by invalid FS). * [misc/registry.c] Two bugs fixed. Fri Mar 13 04:55:01 1998 David Lee Lambert <lamber45@egr.msu.edu> * [include/winnt.h] [include/winnls.h] Moved LANG_xxx flags to winnls.h * [include/winnls.h] Added flags for GetDateFormat(); fixed validity of LOCALE_SYSTEM_DEFAULT. * [include/windows.h] Added GetTimeFormat() prototypes. * [ole/ole2nls.c] Implemented ASCII date- and time-functions, using an optimized common core; added stubs for Unicode versions; started work on a Unicode core. * [AUTHORS] Added my name. Mon Mar 9 20:10:15 1998 Eric Kohl <ekohl@abo.rhein-zeitung.de> * [relay32/comctl32.spec] [include/imagelist.h] [include/commctrl.h] [misc/imagelist.c] [misc/Makefile.in] First attempt at implementing ImageLists. Sun Mar 8 20:19:49 1998 Uwe Bonnes <bon@elektron.ikp.physik.tu-darmstadt.de> * [files/dos_fs.c] [configure.in] Try to get FileTimeToLocalFileTime,FileTimeToSystemTime and SystemTimeToFileTime right. Use timegm() where available. * [misc/lstr.c] Fix an off by one error in FormatMessage and handle the case when args = NULL (used by programs to get the length of the string). * [win32/console.c] Actual display a per-process Title string, better working attempt for WriteConsole32W and ReadConsole32W. Fri Mar 6 20:33:45 1998 Slaven Rezic <eserte@cs.tu-berlin.de> * [include/config.h.in][configure.in][multimedia/audio.c] [multimedia/dsound.c] Added check for FreeBSD sound system. Sun Mar 1 17:40:10 1998 Jason Schonberg <schon@mti.sgi.com> * [controls/edit.c] [include/ole.h] [include/shlobj.h] Removed final commas in enum types. Mon Feb 23 07:52:18 1998 Luiz Otavio L. Zorzella <zorzella@nr.conexware.com> * [multimedia/time.c] Workaround to avoid infinite recursion inside timeGetTime. * [multimedia/audio.c] WODM_GETNUMDEVS and WIDM_GETNUMDEVS only return 1 now if the SOUND_DEV can be opened, or if it's busy.
1998-03-15 21:29:56 +01:00
#include "wine/list.h"
#include "wine/debug.h"
#include "wine/unicode.h"
#include "compobj_private.h"
WINE_DEFAULT_DEBUG_CHANNEL(ole);
/* see MSDN docs for IROTData::GetComparisonData, which states what this
* constant is (http://msdn2.microsoft.com/en-us/library/ms693773.aspx) */
#define MAX_COMPARISON_DATA 2048
/* define the structure of the running object table elements */
struct rot_entry
{
struct list entry;
MInterfacePointer* object; /* marshaled running object*/
MInterfacePointer* moniker; /* marshaled moniker that identifies this object */
MInterfacePointer* moniker_data; /* moniker comparison data that identifies this object */
DWORD cookie; /* cookie identifying this object */
FILETIME last_modified;
};
/* define the RunningObjectTableImpl structure */
typedef struct RunningObjectTableImpl
{
const IRunningObjectTableVtbl *lpVtbl;
2005-07-05 13:02:54 +02:00
LONG ref;
2002-06-01 01:06:46 +02:00
struct list rot; /* list of ROT entries */
CRITICAL_SECTION lock;
} RunningObjectTableImpl;
static RunningObjectTableImpl* runningObjectTableInstance = NULL;
static inline HRESULT WINAPI
IrotRegister(DWORD *cookie)
{
2005-07-05 13:02:54 +02:00
static LONG last_cookie = 1;
*cookie = InterlockedIncrement(&last_cookie);
return S_OK;
}
/* define the EnumMonikerImpl structure */
typedef struct EnumMonikerImpl
{
const IEnumMonikerVtbl *lpVtbl;
2005-07-05 13:02:54 +02:00
LONG ref;
MInterfacePointer **monikers;
ULONG moniker_count;
ULONG pos;
} EnumMonikerImpl;
/* IEnumMoniker Local functions*/
static HRESULT WINAPI EnumMonikerImpl_CreateEnumROTMoniker(MInterfacePointer **monikers,
ULONG moniker_count, ULONG pos, IEnumMoniker **ppenumMoniker);
static HRESULT create_stream_on_mip_ro(const MInterfacePointer *mip, IStream **stream)
{
HGLOBAL hglobal = GlobalAlloc(0, mip->ulCntData);
void *pv = GlobalLock(hglobal);
memcpy(pv, mip->abData, mip->ulCntData);
GlobalUnlock(hglobal);
return CreateStreamOnHGlobal(hglobal, TRUE, stream);
}
static inline void rot_entry_delete(struct rot_entry *rot_entry)
{
/* FIXME: revoke entry from rpcss's copy of the ROT */
if (rot_entry->object)
{
IStream *stream;
HRESULT hr;
hr = create_stream_on_mip_ro(rot_entry->object, &stream);
if (hr == S_OK)
{
CoReleaseMarshalData(stream);
IUnknown_Release(stream);
}
}
if (rot_entry->moniker)
{
IStream *stream;
HRESULT hr;
hr = create_stream_on_mip_ro(rot_entry->moniker, &stream);
if (hr == S_OK)
{
CoReleaseMarshalData(stream);
IUnknown_Release(stream);
}
}
HeapFree(GetProcessHeap(), 0, rot_entry->object);
HeapFree(GetProcessHeap(), 0, rot_entry->moniker);
HeapFree(GetProcessHeap(), 0, rot_entry->moniker_data);
HeapFree(GetProcessHeap(), 0, rot_entry);
}
/* moniker_data must be freed with HeapFree when no longer in use */
static HRESULT get_moniker_comparison_data(IMoniker *pMoniker, MInterfacePointer **moniker_data)
{
HRESULT hr;
IROTData *pROTData = NULL;
hr = IMoniker_QueryInterface(pMoniker, &IID_IROTData, (void *)&pROTData);
if (SUCCEEDED(hr))
{
ULONG size = MAX_COMPARISON_DATA;
*moniker_data = HeapAlloc(GetProcessHeap(), 0, FIELD_OFFSET(MInterfacePointer, abData[size]));
hr = IROTData_GetComparisonData(pROTData, (*moniker_data)->abData, size, &size);
if (hr != S_OK)
{
ERR("Failed to copy comparison data into buffer, hr = 0x%08x\n", hr);
HeapFree(GetProcessHeap(), 0, *moniker_data);
return hr;
}
(*moniker_data)->ulCntData = size;
}
else
{
IBindCtx *pbc;
LPOLESTR pszDisplayName;
CLSID clsid;
int len;
TRACE("generating comparison data from display name\n");
hr = CreateBindCtx(0, &pbc);
if (FAILED(hr))
return hr;
hr = IMoniker_GetDisplayName(pMoniker, pbc, NULL, &pszDisplayName);
IBindCtx_Release(pbc);
if (FAILED(hr))
return hr;
hr = IMoniker_GetClassID(pMoniker, &clsid);
if (FAILED(hr))
{
CoTaskMemFree(pszDisplayName);
return hr;
}
len = strlenW(pszDisplayName);
*moniker_data = HeapAlloc(GetProcessHeap(), 0,
FIELD_OFFSET(MInterfacePointer, abData[sizeof(CLSID) + (len+1)*sizeof(WCHAR)]));
if (!*moniker_data)
{
CoTaskMemFree(pszDisplayName);
return E_OUTOFMEMORY;
}
(*moniker_data)->ulCntData = sizeof(CLSID) + (len+1)*sizeof(WCHAR);
memcpy(&(*moniker_data)->abData[0], &clsid, sizeof(clsid));
memcpy(&(*moniker_data)->abData[sizeof(clsid)], pszDisplayName, (len+1)*sizeof(WCHAR));
}
return S_OK;
}
static HRESULT reduce_moniker(IMoniker *pmk, IBindCtx *pbc, IMoniker **pmkReduced)
{
IBindCtx *pbcNew = NULL;
HRESULT hr;
if (!pbc)
{
hr = CreateBindCtx(0, &pbcNew);
if (FAILED(hr))
return hr;
pbc = pbcNew;
}
hr = IMoniker_Reduce(pmk, pbc, MKRREDUCE_ALL, NULL, pmkReduced);
if (FAILED(hr))
ERR("reducing moniker failed with error 0x%08x\n", hr);
if (pbcNew) IBindCtx_Release(pbcNew);
return hr;
}
/***********************************************************************
* RunningObjectTable_QueryInterface
Release 980315 Sun Mar 15 03:46:50 1998 Dimitrie O. Paun <dimi@mail.cs.toronto.edu> * [*/*] Fixed some dprintf_ such that there is one and only one new line for each dprintf and that new line occurs at the end. Transformed some fprintfs into proper debug statements. Removed much redundancy from most of the debug statements. The redundancy appeared because now the component and function name is output automatically. Most debug statements also used to output the name of the function. All these changes prepared the source to switch completely to the new debugging interface. For more info, refer to ./documentation/debug-msg Sat Mar 14 19:45:23 1997 Andreas Mohr <100.30936@germany.net> * [misc/shell.c] [if1632/kernel.spec] Changed parameters of FUNC004() to fix a crash. Not sure if this fix is correct (doc wanted). * [windows/user.c] [if1632/user.spec] [include/user.h] Implemented UserSeeUserDo. * [msdos/int21.c] [include/msdos.h] Added "GET LIST OF LISTS" (INT 21/52h). Sat Mar 14 15:48:02 1998 Douglas Ridgway <ridgway@gmcl.com> * [include/windows.h] [relay32/gdi32.spec] [objects/enhmetafile.c] Beginnings of enhanced metafile support. Fri Mar 13 20:53:09 1998 John Richardson <jrichard@zko.dec.com> * [win32/console.c] Restart interrupted console writes. Fri Mar 13 18:59:24 1998 Matthew Becker <mbecker@glasscity.net> * [*/*.c] Updated documentation for API manpages. * [windows/dce.c] ReleaseDC16: Fixed cast. * [include/windows.h] [memory/virtual.c] VirtualQuery{Ex} should return DWORD instead of BOOL32. Fri Mar 13 13:03:06 1998 Marcus Meissner <msmeissn@cip.informatik.uni-erlangen.de> * [README][documentation/status/] README updated, added lzexpand,version and multimedia status notes to new documentation/status directory. * [ole/*.c][if1632/typelib.spec] Added typelib stubs, several small additions and fixes. * [loader/pe_image.c] Fixed a small bug (fixup_imports got passed the wrong hModule in a remapcase). * [loader/signal.c][if1632/signal.c][misc/winsock_dns.c] [loader/module.c] Fixed some recursive debugger crashes (caused by invalid FS). * [misc/registry.c] Two bugs fixed. Fri Mar 13 04:55:01 1998 David Lee Lambert <lamber45@egr.msu.edu> * [include/winnt.h] [include/winnls.h] Moved LANG_xxx flags to winnls.h * [include/winnls.h] Added flags for GetDateFormat(); fixed validity of LOCALE_SYSTEM_DEFAULT. * [include/windows.h] Added GetTimeFormat() prototypes. * [ole/ole2nls.c] Implemented ASCII date- and time-functions, using an optimized common core; added stubs for Unicode versions; started work on a Unicode core. * [AUTHORS] Added my name. Mon Mar 9 20:10:15 1998 Eric Kohl <ekohl@abo.rhein-zeitung.de> * [relay32/comctl32.spec] [include/imagelist.h] [include/commctrl.h] [misc/imagelist.c] [misc/Makefile.in] First attempt at implementing ImageLists. Sun Mar 8 20:19:49 1998 Uwe Bonnes <bon@elektron.ikp.physik.tu-darmstadt.de> * [files/dos_fs.c] [configure.in] Try to get FileTimeToLocalFileTime,FileTimeToSystemTime and SystemTimeToFileTime right. Use timegm() where available. * [misc/lstr.c] Fix an off by one error in FormatMessage and handle the case when args = NULL (used by programs to get the length of the string). * [win32/console.c] Actual display a per-process Title string, better working attempt for WriteConsole32W and ReadConsole32W. Fri Mar 6 20:33:45 1998 Slaven Rezic <eserte@cs.tu-berlin.de> * [include/config.h.in][configure.in][multimedia/audio.c] [multimedia/dsound.c] Added check for FreeBSD sound system. Sun Mar 1 17:40:10 1998 Jason Schonberg <schon@mti.sgi.com> * [controls/edit.c] [include/ole.h] [include/shlobj.h] Removed final commas in enum types. Mon Feb 23 07:52:18 1998 Luiz Otavio L. Zorzella <zorzella@nr.conexware.com> * [multimedia/time.c] Workaround to avoid infinite recursion inside timeGetTime. * [multimedia/audio.c] WODM_GETNUMDEVS and WIDM_GETNUMDEVS only return 1 now if the SOUND_DEV can be opened, or if it's busy.
1998-03-15 21:29:56 +01:00
*/
static HRESULT WINAPI
RunningObjectTableImpl_QueryInterface(IRunningObjectTable* iface,
REFIID riid,void** ppvObject)
{
RunningObjectTableImpl *This = (RunningObjectTableImpl *)iface;
TRACE("(%p,%p,%p)\n",This,riid,ppvObject);
/* validate arguments */
if (ppvObject==0)
return E_INVALIDARG;
*ppvObject = 0;
if (IsEqualIID(&IID_IUnknown, riid) ||
IsEqualIID(&IID_IRunningObjectTable, riid))
*ppvObject = (IRunningObjectTable*)This;
if ((*ppvObject)==0)
return E_NOINTERFACE;
IRunningObjectTable_AddRef(iface);
return S_OK;
}
/***********************************************************************
* RunningObjectTable_AddRef
*/
static ULONG WINAPI
RunningObjectTableImpl_AddRef(IRunningObjectTable* iface)
{
RunningObjectTableImpl *This = (RunningObjectTableImpl *)iface;
TRACE("(%p)\n",This);
2004-09-24 03:16:53 +02:00
return InterlockedIncrement(&This->ref);
}
/***********************************************************************
* RunningObjectTable_Initialize
*/
static HRESULT WINAPI
RunningObjectTableImpl_Destroy(void)
{
struct list *cursor, *cursor2;
TRACE("()\n");
2002-06-01 01:06:46 +02:00
if (runningObjectTableInstance==NULL)
return E_INVALIDARG;
/* free the ROT table memory */
LIST_FOR_EACH_SAFE(cursor, cursor2, &runningObjectTableInstance->rot)
{
struct rot_entry *rot_entry = LIST_ENTRY(cursor, struct rot_entry, entry);
list_remove(&rot_entry->entry);
rot_entry_delete(rot_entry);
}
/* free the ROT structure memory */
HeapFree(GetProcessHeap(),0,runningObjectTableInstance);
runningObjectTableInstance = NULL;
return S_OK;
}
/***********************************************************************
* RunningObjectTable_Release
*/
static ULONG WINAPI
RunningObjectTableImpl_Release(IRunningObjectTable* iface)
{
RunningObjectTableImpl *This = (RunningObjectTableImpl *)iface;
2004-09-24 03:16:53 +02:00
ULONG ref;
TRACE("(%p)\n",This);
2004-09-24 03:16:53 +02:00
ref = InterlockedDecrement(&This->ref);
/* uninitialize ROT structure if there's no more references to it */
if (ref == 0)
{
struct list *cursor, *cursor2;
LIST_FOR_EACH_SAFE(cursor, cursor2, &This->rot)
{
struct rot_entry *rot_entry = LIST_ENTRY(cursor, struct rot_entry, entry);
list_remove(&rot_entry->entry);
rot_entry_delete(rot_entry);
}
/* RunningObjectTable data structure will be not destroyed here ! the destruction will be done only
* when RunningObjectTableImpl_UnInitialize function is called
*/
}
2004-09-24 03:16:53 +02:00
return ref;
}
/***********************************************************************
* RunningObjectTable_Register
*
* PARAMS
* grfFlags [in] Registration options
* punkObject [in] the object being registered
* pmkObjectName [in] the moniker of the object being registered
* pdwRegister [in] the value identifying the registration
*/
static HRESULT WINAPI
RunningObjectTableImpl_Register(IRunningObjectTable* iface, DWORD grfFlags,
IUnknown *punkObject, IMoniker *pmkObjectName, DWORD *pdwRegister)
{
RunningObjectTableImpl *This = (RunningObjectTableImpl *)iface;
struct rot_entry *rot_entry;
HRESULT hr = S_OK;
IStream *pStream = NULL;
DWORD mshlflags;
IBindCtx *pbc;
TRACE("(%p,%d,%p,%p,%p)\n",This,grfFlags,punkObject,pmkObjectName,pdwRegister);
if (grfFlags & ~(ROTFLAGS_REGISTRATIONKEEPSALIVE|ROTFLAGS_ALLOWANYCLIENT))
{
ERR("Invalid grfFlags: 0x%08x\n", grfFlags & ~(ROTFLAGS_REGISTRATIONKEEPSALIVE|ROTFLAGS_ALLOWANYCLIENT));
return E_INVALIDARG;
}
if (punkObject==NULL || pmkObjectName==NULL || pdwRegister==NULL)
return E_INVALIDARG;
rot_entry = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, sizeof(*rot_entry));
if (!rot_entry)
return E_OUTOFMEMORY;
/* marshal object */
hr = CreateStreamOnHGlobal(NULL, TRUE, &pStream);
if (hr != S_OK)
{
rot_entry_delete(rot_entry);
return hr;
}
mshlflags = (grfFlags & ROTFLAGS_REGISTRATIONKEEPSALIVE) ? MSHLFLAGS_TABLESTRONG : MSHLFLAGS_TABLEWEAK;
hr = CoMarshalInterface(pStream, &IID_IUnknown, punkObject, MSHCTX_LOCAL | MSHCTX_NOSHAREDMEM, NULL, mshlflags);
/* FIXME: a cleaner way would be to create an IStream class that writes
* directly to an MInterfacePointer */
if (hr == S_OK)
{
HGLOBAL hglobal;
hr = GetHGlobalFromStream(pStream, &hglobal);
if (hr == S_OK)
{
SIZE_T size = GlobalSize(hglobal);
const void *pv = GlobalLock(hglobal);
rot_entry->object = HeapAlloc(GetProcessHeap(), 0, FIELD_OFFSET(MInterfacePointer, abData[size]));
rot_entry->object->ulCntData = size;
memcpy(&rot_entry->object->abData, pv, size);
GlobalUnlock(hglobal);
}
}
IStream_Release(pStream);
if (hr != S_OK)
{
rot_entry_delete(rot_entry);
return hr;
}
2002-06-01 01:06:46 +02:00
hr = CreateBindCtx(0, &pbc);
if (FAILED(hr))
{
rot_entry_delete(rot_entry);
return hr;
}
hr = reduce_moniker(pmkObjectName, pbc, &pmkObjectName);
if (FAILED(hr))
{
rot_entry_delete(rot_entry);
IBindCtx_Release(pbc);
return hr;
}
hr = IMoniker_GetTimeOfLastChange(pmkObjectName, pbc, NULL,
&rot_entry->last_modified);
IBindCtx_Release(pbc);
if (FAILED(hr))
{
CoFileTimeNow(&rot_entry->last_modified);
hr = S_OK;
}
hr = get_moniker_comparison_data(pmkObjectName,
&rot_entry->moniker_data);
if (hr != S_OK)
{
rot_entry_delete(rot_entry);
IMoniker_Release(pmkObjectName);
return hr;
}
hr = CreateStreamOnHGlobal(NULL, TRUE, &pStream);
if (hr != S_OK)
{
rot_entry_delete(rot_entry);
IMoniker_Release(pmkObjectName);
return hr;
}
/* marshal moniker */
hr = CoMarshalInterface(pStream, &IID_IMoniker, (IUnknown *)pmkObjectName,
MSHCTX_LOCAL | MSHCTX_NOSHAREDMEM, NULL, MSHLFLAGS_TABLESTRONG);
/* FIXME: a cleaner way would be to create an IStream class that writes
* directly to an MInterfacePointer */
if (hr == S_OK)
{
HGLOBAL hglobal;
hr = GetHGlobalFromStream(pStream, &hglobal);
if (hr == S_OK)
{
SIZE_T size = GlobalSize(hglobal);
const void *pv = GlobalLock(hglobal);
rot_entry->moniker = HeapAlloc(GetProcessHeap(), 0, FIELD_OFFSET(MInterfacePointer, abData[size]));
rot_entry->moniker->ulCntData = size;
memcpy(&rot_entry->moniker->abData, pv, size);
GlobalUnlock(hglobal);
}
}
IStream_Release(pStream);
IMoniker_Release(pmkObjectName);
if (hr != S_OK)
{
rot_entry_delete(rot_entry);
return hr;
}
2002-06-01 01:06:46 +02:00
/* FIXME: not the right signature of IrotRegister function */
hr = IrotRegister(&rot_entry->cookie);
if (hr != S_OK)
{
rot_entry_delete(rot_entry);
return hr;
}
/* gives a registration identifier to the registered object*/
*pdwRegister = rot_entry->cookie;
EnterCriticalSection(&This->lock);
/* FIXME: see if object was registered before and return MK_S_MONIKERALREADYREGISTERED */
list_add_tail(&This->rot, &rot_entry->entry);
LeaveCriticalSection(&This->lock);
return hr;
}
/***********************************************************************
* RunningObjectTable_Revoke
*
* PARAMS
* dwRegister [in] Value identifying registration to be revoked
*/
static HRESULT WINAPI
RunningObjectTableImpl_Revoke( IRunningObjectTable* iface, DWORD dwRegister)
{
RunningObjectTableImpl *This = (RunningObjectTableImpl *)iface;
struct rot_entry *rot_entry;
TRACE("(%p,%d)\n",This,dwRegister);
EnterCriticalSection(&This->lock);
LIST_FOR_EACH_ENTRY(rot_entry, &This->rot, struct rot_entry, entry)
{
if (rot_entry->cookie == dwRegister)
{
list_remove(&rot_entry->entry);
LeaveCriticalSection(&This->lock);
rot_entry_delete(rot_entry);
return S_OK;
}
}
LeaveCriticalSection(&This->lock);
2002-06-01 01:06:46 +02:00
return E_INVALIDARG;
}
/***********************************************************************
* RunningObjectTable_IsRunning
*
* PARAMS
* pmkObjectName [in] moniker of the object whose status is desired
*/
static HRESULT WINAPI
RunningObjectTableImpl_IsRunning( IRunningObjectTable* iface, IMoniker *pmkObjectName)
2002-06-01 01:06:46 +02:00
{
RunningObjectTableImpl *This = (RunningObjectTableImpl *)iface;
MInterfacePointer *moniker_data;
HRESULT hr;
struct rot_entry *rot_entry;
TRACE("(%p,%p)\n",This,pmkObjectName);
hr = reduce_moniker(pmkObjectName, NULL, &pmkObjectName);
if (FAILED(hr))
return hr;
hr = get_moniker_comparison_data(pmkObjectName, &moniker_data);
IMoniker_Release(pmkObjectName);
if (hr != S_OK)
return hr;
hr = S_FALSE;
EnterCriticalSection(&This->lock);
LIST_FOR_EACH_ENTRY(rot_entry, &This->rot, struct rot_entry, entry)
{
if ((rot_entry->moniker_data->ulCntData == moniker_data->ulCntData) &&
!memcmp(&moniker_data->abData, &rot_entry->moniker_data->abData, moniker_data->ulCntData))
{
hr = S_OK;
break;
}
}
LeaveCriticalSection(&This->lock);
/* FIXME: call IrotIsRunning */
HeapFree(GetProcessHeap(), 0, moniker_data);
return hr;
}
/***********************************************************************
* RunningObjectTable_GetObject
*
* PARAMS
* pmkObjectName [in] Pointer to the moniker on the object
* ppunkObject [out] variable that receives the IUnknown interface pointer
*/
static HRESULT WINAPI
RunningObjectTableImpl_GetObject( IRunningObjectTable* iface,
IMoniker *pmkObjectName, IUnknown **ppunkObject)
{
RunningObjectTableImpl *This = (RunningObjectTableImpl *)iface;
MInterfacePointer *moniker_data;
HRESULT hr;
struct rot_entry *rot_entry;
TRACE("(%p,%p,%p)\n",This,pmkObjectName,ppunkObject);
if (ppunkObject == NULL)
return E_POINTER;
2002-06-01 01:06:46 +02:00
*ppunkObject = NULL;
hr = reduce_moniker(pmkObjectName, NULL, &pmkObjectName);
if (FAILED(hr))
return hr;
hr = get_moniker_comparison_data(pmkObjectName, &moniker_data);
IMoniker_Release(pmkObjectName);
if (hr != S_OK)
return hr;
EnterCriticalSection(&This->lock);
LIST_FOR_EACH_ENTRY(rot_entry, &This->rot, struct rot_entry, entry)
{
if ((rot_entry->moniker_data->ulCntData == moniker_data->ulCntData) &&
!memcmp(&moniker_data->abData, &rot_entry->moniker_data->abData, moniker_data->ulCntData))
{
IStream *pStream;
hr = create_stream_on_mip_ro(rot_entry->object, &pStream);
if (hr == S_OK)
{
hr = CoUnmarshalInterface(pStream, &IID_IUnknown, (void **)ppunkObject);
IStream_Release(pStream);
}
LeaveCriticalSection(&This->lock);
HeapFree(GetProcessHeap(), 0, moniker_data);
return hr;
}
}
LeaveCriticalSection(&This->lock);
/* FIXME: call IrotGetObject */
WARN("Moniker unavailable - app may require interprocess running object table\n");
hr = MK_E_UNAVAILABLE;
HeapFree(GetProcessHeap(), 0, moniker_data);
return hr;
}
1998-11-22 18:56:07 +01:00
/***********************************************************************
* RunningObjectTable_NoteChangeTime
*
* PARAMS
* dwRegister [in] Value identifying registration being updated
* pfiletime [in] Pointer to structure containing object's last change time
1998-11-22 18:56:07 +01:00
*/
static HRESULT WINAPI
RunningObjectTableImpl_NoteChangeTime(IRunningObjectTable* iface,
DWORD dwRegister, FILETIME *pfiletime)
{
RunningObjectTableImpl *This = (RunningObjectTableImpl *)iface;
struct rot_entry *rot_entry;
TRACE("(%p,%d,%p)\n",This,dwRegister,pfiletime);
EnterCriticalSection(&This->lock);
LIST_FOR_EACH_ENTRY(rot_entry, &This->rot, struct rot_entry, entry)
{
if (rot_entry->cookie == dwRegister)
{
rot_entry->last_modified = *pfiletime;
LeaveCriticalSection(&This->lock);
return S_OK;
}
}
LeaveCriticalSection(&This->lock);
/* FIXME: call IrotNoteChangeTime */
return E_INVALIDARG;
}
2002-06-01 01:06:46 +02:00
/***********************************************************************
* RunningObjectTable_GetTimeOfLastChange
*
* PARAMS
* pmkObjectName [in] moniker of the object whose status is desired
* pfiletime [out] structure that receives object's last change time
*/
static HRESULT WINAPI
RunningObjectTableImpl_GetTimeOfLastChange(IRunningObjectTable* iface,
IMoniker *pmkObjectName, FILETIME *pfiletime)
{
HRESULT hr = MK_E_UNAVAILABLE;
RunningObjectTableImpl *This = (RunningObjectTableImpl *)iface;
MInterfacePointer *moniker_data;
struct rot_entry *rot_entry;
TRACE("(%p,%p,%p)\n",This,pmkObjectName,pfiletime);
if (pmkObjectName==NULL || pfiletime==NULL)
return E_INVALIDARG;
hr = reduce_moniker(pmkObjectName, NULL, &pmkObjectName);
if (FAILED(hr))
return hr;
hr = get_moniker_comparison_data(pmkObjectName, &moniker_data);
IMoniker_Release(pmkObjectName);
if (hr != S_OK)
return hr;
hr = MK_E_UNAVAILABLE;
EnterCriticalSection(&This->lock);
LIST_FOR_EACH_ENTRY(rot_entry, &This->rot, struct rot_entry, entry)
{
if ((rot_entry->moniker_data->ulCntData == moniker_data->ulCntData) &&
!memcmp(&moniker_data->abData, &rot_entry->moniker_data->abData, moniker_data->ulCntData))
{
*pfiletime = rot_entry->last_modified;
hr = S_OK;
break;
}
}
LeaveCriticalSection(&This->lock);
/* FIXME: if (hr != S_OK) call IrotGetTimeOfLastChange */
HeapFree(GetProcessHeap(), 0, moniker_data);
return hr;
}
/***********************************************************************
* RunningObjectTable_EnumRunning
*
* PARAMS
* ppenumMoniker [out] receives the IEnumMoniker interface pointer
*/
static HRESULT WINAPI
RunningObjectTableImpl_EnumRunning(IRunningObjectTable* iface,
IEnumMoniker **ppenumMoniker)
{
HRESULT hr;
RunningObjectTableImpl *This = (RunningObjectTableImpl *)iface;
MInterfacePointer **monikers;
ULONG moniker_count = 0;
const struct rot_entry *rot_entry;
ULONG i = 0;
EnterCriticalSection(&This->lock);
LIST_FOR_EACH_ENTRY( rot_entry, &This->rot, const struct rot_entry, entry )
moniker_count++;
monikers = HeapAlloc(GetProcessHeap(), 0, moniker_count * sizeof(*monikers));
LIST_FOR_EACH_ENTRY( rot_entry, &This->rot, const struct rot_entry, entry )
{
SIZE_T size = FIELD_OFFSET(MInterfacePointer, abData[rot_entry->moniker->ulCntData]);
monikers[i] = HeapAlloc(GetProcessHeap(), 0, size);
memcpy(monikers[i], rot_entry->moniker, size);
i++;
}
2002-06-01 01:06:46 +02:00
LeaveCriticalSection(&This->lock);
/* FIXME: call IrotEnumRunning and append data */
hr = EnumMonikerImpl_CreateEnumROTMoniker(monikers, moniker_count, 0, ppenumMoniker);
return hr;
}
/***********************************************************************
2003-09-11 05:06:25 +02:00
* GetRunningObjectTable (OLE32.@)
*/
HRESULT WINAPI
GetRunningObjectTable(DWORD reserved, LPRUNNINGOBJECTTABLE *pprot)
{
IID riid=IID_IRunningObjectTable;
HRESULT res;
TRACE("()\n");
if (reserved!=0)
return E_UNEXPECTED;
if(runningObjectTableInstance==NULL)
return CO_E_NOTINITIALIZED;
res = IRunningObjectTable_QueryInterface((IRunningObjectTable*)runningObjectTableInstance,&riid,(void**)pprot);
return res;
1998-11-22 18:56:07 +01:00
}
2000-01-15 23:14:20 +01:00
/******************************************************************************
2003-09-11 05:06:25 +02:00
* OleRun [OLE32.@]
2000-01-15 23:14:20 +01:00
*/
HRESULT WINAPI OleRun(LPUNKNOWN pUnknown)
{
IRunnableObject *runable;
2006-08-02 21:29:04 +02:00
HRESULT hres;
2006-08-02 21:29:04 +02:00
TRACE("(%p)\n", pUnknown);
hres = IUnknown_QueryInterface(pUnknown, &IID_IRunnableObject, (void**)&runable);
if (FAILED(hres))
return S_OK; /* Appears to return no error. */
hres = IRunnableObject_Run(runable, NULL);
IRunnableObject_Release(runable);
2006-08-02 21:29:04 +02:00
return hres;
2000-01-15 23:14:20 +01:00
}
/******************************************************************************
2003-09-11 05:06:25 +02:00
* MkParseDisplayName [OLE32.@]
*/
2000-06-07 04:15:39 +02:00
HRESULT WINAPI MkParseDisplayName(LPBC pbc, LPCOLESTR szUserName,
LPDWORD pchEaten, LPMONIKER *ppmk)
{
FIXME("(%p, %s, %p, %p): stub.\n", pbc, debugstr_w(szUserName), pchEaten, *ppmk);
2000-03-08 19:25:22 +01:00
if (!(IsValidInterface((LPUNKNOWN) pbc)))
return E_INVALIDARG;
return MK_E_SYNTAX;
}
2003-07-19 00:59:58 +02:00
/* Virtual function table for the IRunningObjectTable class. */
static const IRunningObjectTableVtbl VT_RunningObjectTableImpl =
{
RunningObjectTableImpl_QueryInterface,
RunningObjectTableImpl_AddRef,
RunningObjectTableImpl_Release,
RunningObjectTableImpl_Register,
RunningObjectTableImpl_Revoke,
RunningObjectTableImpl_IsRunning,
RunningObjectTableImpl_GetObject,
RunningObjectTableImpl_NoteChangeTime,
RunningObjectTableImpl_GetTimeOfLastChange,
RunningObjectTableImpl_EnumRunning
};
/***********************************************************************
* RunningObjectTable_Initialize
*/
HRESULT WINAPI RunningObjectTableImpl_Initialize(void)
{
TRACE("\n");
/* create the unique instance of the RunningObjectTableImpl structure */
runningObjectTableInstance = HeapAlloc(GetProcessHeap(), 0, sizeof(RunningObjectTableImpl));
if (!runningObjectTableInstance)
return E_OUTOFMEMORY;
/* initialize the virtual table function */
runningObjectTableInstance->lpVtbl = &VT_RunningObjectTableImpl;
/* the initial reference is set to "1" ! because if set to "0" it will be not practis when */
/* the ROT referred many times not in the same time (all the objects in the ROT will */
/* be removed every time the ROT is removed ) */
runningObjectTableInstance->ref = 1;
list_init(&runningObjectTableInstance->rot);
InitializeCriticalSection(&runningObjectTableInstance->lock);
return S_OK;
}
/***********************************************************************
* RunningObjectTable_UnInitialize
*/
HRESULT WINAPI RunningObjectTableImpl_UnInitialize()
{
TRACE("\n");
if (runningObjectTableInstance==NULL)
return E_POINTER;
RunningObjectTableImpl_Release((IRunningObjectTable*)runningObjectTableInstance);
RunningObjectTableImpl_Destroy();
return S_OK;
}
/***********************************************************************
* EnumMoniker_QueryInterface
*/
static HRESULT WINAPI EnumMonikerImpl_QueryInterface(IEnumMoniker* iface,REFIID riid,void** ppvObject)
{
EnumMonikerImpl *This = (EnumMonikerImpl *)iface;
TRACE("(%p,%p,%p)\n",This,riid,ppvObject);
/* validate arguments */
if (ppvObject == NULL)
return E_INVALIDARG;
*ppvObject = NULL;
if (IsEqualIID(&IID_IUnknown, riid))
*ppvObject = (IEnumMoniker*)This;
else
if (IsEqualIID(&IID_IEnumMoniker, riid))
*ppvObject = (IEnumMoniker*)This;
if ((*ppvObject)==NULL)
return E_NOINTERFACE;
IEnumMoniker_AddRef(iface);
return S_OK;
}
/***********************************************************************
* EnumMoniker_AddRef
*/
static ULONG WINAPI EnumMonikerImpl_AddRef(IEnumMoniker* iface)
{
EnumMonikerImpl *This = (EnumMonikerImpl *)iface;
TRACE("(%p)\n",This);
return InterlockedIncrement(&This->ref);
}
/***********************************************************************
* EnumMoniker_release
*/
static ULONG WINAPI EnumMonikerImpl_Release(IEnumMoniker* iface)
{
EnumMonikerImpl *This = (EnumMonikerImpl *)iface;
ULONG ref;
TRACE("(%p)\n",This);
ref = InterlockedDecrement(&This->ref);
2006-11-12 19:51:37 +01:00
/* uninitialize rot structure if there's no more reference to it*/
if (ref == 0)
{
ULONG i;
TRACE("(%p) Deleting\n",This);
for (i = 0; i < This->moniker_count; i++)
HeapFree(GetProcessHeap(), 0, This->monikers[i]);
HeapFree(GetProcessHeap(), 0, This->monikers);
HeapFree(GetProcessHeap(), 0, This);
}
return ref;
}
/***********************************************************************
* EnmumMoniker_Next
*/
static HRESULT WINAPI EnumMonikerImpl_Next(IEnumMoniker* iface, ULONG celt, IMoniker** rgelt, ULONG * pceltFetched)
{
ULONG i;
EnumMonikerImpl *This = (EnumMonikerImpl *)iface;
HRESULT hr = S_OK;
TRACE("(%p) TabCurrentPos %d Tablastindx %d\n", This, This->pos, This->moniker_count);
/* retrieve the requested number of moniker from the current position */
for(i = 0; (This->pos < This->moniker_count) && (i < celt); i++)
{
IStream *stream;
hr = create_stream_on_mip_ro(This->monikers[This->pos++], &stream);
if (hr != S_OK) break;
hr = CoUnmarshalInterface(stream, &IID_IMoniker, (void **)&rgelt[i]);
IStream_Release(stream);
if (hr != S_OK) break;
}
if (pceltFetched != NULL)
*pceltFetched= i;
if (hr != S_OK)
return hr;
if (i == celt)
return S_OK;
else
return S_FALSE;
}
/***********************************************************************
* EnmumMoniker_Skip
*/
static HRESULT WINAPI EnumMonikerImpl_Skip(IEnumMoniker* iface, ULONG celt)
{
EnumMonikerImpl *This = (EnumMonikerImpl *)iface;
TRACE("(%p)\n",This);
if (This->pos + celt >= This->moniker_count)
return S_FALSE;
This->pos += celt;
return S_OK;
}
/***********************************************************************
* EnmumMoniker_Reset
*/
static HRESULT WINAPI EnumMonikerImpl_Reset(IEnumMoniker* iface)
{
EnumMonikerImpl *This = (EnumMonikerImpl *)iface;
This->pos = 0; /* set back to start of list */
TRACE("(%p)\n",This);
return S_OK;
}
/***********************************************************************
* EnmumMoniker_Clone
*/
static HRESULT WINAPI EnumMonikerImpl_Clone(IEnumMoniker* iface, IEnumMoniker ** ppenum)
{
EnumMonikerImpl *This = (EnumMonikerImpl *)iface;
MInterfacePointer **monikers = HeapAlloc(GetProcessHeap(), 0, sizeof(*monikers)*This->moniker_count);
ULONG i;
TRACE("(%p)\n",This);
for (i = 0; i < This->moniker_count; i++)
{
SIZE_T size = FIELD_OFFSET(MInterfacePointer, abData[This->monikers[i]->ulCntData]);
monikers[i] = HeapAlloc(GetProcessHeap(), 0, size);
memcpy(monikers[i], This->monikers[i], size);
}
/* copy the enum structure */
return EnumMonikerImpl_CreateEnumROTMoniker(monikers, This->moniker_count,
This->pos, ppenum);
}
/* Virtual function table for the IEnumMoniker class. */
static const IEnumMonikerVtbl VT_EnumMonikerImpl =
{
EnumMonikerImpl_QueryInterface,
EnumMonikerImpl_AddRef,
EnumMonikerImpl_Release,
EnumMonikerImpl_Next,
EnumMonikerImpl_Skip,
EnumMonikerImpl_Reset,
EnumMonikerImpl_Clone
};
/***********************************************************************
* EnumMonikerImpl_CreateEnumROTMoniker
* Used by EnumRunning to create the structure and EnumClone
* to copy the structure
*/
static HRESULT WINAPI EnumMonikerImpl_CreateEnumROTMoniker(MInterfacePointer **monikers,
ULONG moniker_count,
ULONG current_pos,
IEnumMoniker **ppenumMoniker)
{
EnumMonikerImpl* This = NULL;
if (!ppenumMoniker)
return E_INVALIDARG;
This = HeapAlloc(GetProcessHeap(), 0, sizeof(EnumMonikerImpl));
if (!This) return E_OUTOFMEMORY;
TRACE("(%p)\n", This);
/* initialize the virtual table function */
This->lpVtbl = &VT_EnumMonikerImpl;
/* the initial reference is set to "1" */
This->ref = 1; /* set the ref count to one */
2005-06-02 22:06:22 +02:00
This->pos = current_pos; /* Set the list start posn */
This->moniker_count = moniker_count; /* Need the same size table as ROT */
This->monikers = monikers;
*ppenumMoniker = (IEnumMoniker*)This;
return S_OK;
}
/* Shared implementation of moniker marshaler based on saving and loading of
* monikers */
typedef struct MonikerMarshal
{
const IUnknownVtbl *lpVtbl;
const IMarshalVtbl *lpVtblMarshal;
2005-07-05 13:02:54 +02:00
LONG ref;
IMoniker *moniker;
} MonikerMarshal;
static inline MonikerMarshal *impl_from_IMarshal( IMarshal *iface )
{
return (MonikerMarshal *)((char*)iface - FIELD_OFFSET(MonikerMarshal, lpVtblMarshal));
}
static HRESULT WINAPI MonikerMarshalInner_QueryInterface(IUnknown *iface, REFIID riid, LPVOID *ppv)
{
MonikerMarshal *This = (MonikerMarshal *)iface;
TRACE("(%s, %p)\n", debugstr_guid(riid), ppv);
*ppv = NULL;
if (IsEqualIID(&IID_IUnknown, riid) || IsEqualIID(&IID_IMarshal, riid))
{
*ppv = &This->lpVtblMarshal;
IUnknown_AddRef((IUnknown *)&This->lpVtblMarshal);
return S_OK;
}
FIXME("No interface for %s\n", debugstr_guid(riid));
return E_NOINTERFACE;
}
static ULONG WINAPI MonikerMarshalInner_AddRef(IUnknown *iface)
{
MonikerMarshal *This = (MonikerMarshal *)iface;
return InterlockedIncrement(&This->ref);
}
static ULONG WINAPI MonikerMarshalInner_Release(IUnknown *iface)
{
MonikerMarshal *This = (MonikerMarshal *)iface;
ULONG ref = InterlockedDecrement(&This->ref);
if (!ref) HeapFree(GetProcessHeap(), 0, This);
return ref;
}
static const IUnknownVtbl VT_MonikerMarshalInner =
{
MonikerMarshalInner_QueryInterface,
MonikerMarshalInner_AddRef,
MonikerMarshalInner_Release
};
static HRESULT WINAPI MonikerMarshal_QueryInterface(IMarshal *iface, REFIID riid, LPVOID *ppv)
{
MonikerMarshal *This = impl_from_IMarshal(iface);
return IMoniker_QueryInterface(This->moniker, riid, ppv);
}
static ULONG WINAPI MonikerMarshal_AddRef(IMarshal *iface)
{
MonikerMarshal *This = impl_from_IMarshal(iface);
return IMoniker_AddRef(This->moniker);
}
static ULONG WINAPI MonikerMarshal_Release(IMarshal *iface)
{
MonikerMarshal *This = impl_from_IMarshal(iface);
return IMoniker_Release(This->moniker);
}
static HRESULT WINAPI MonikerMarshal_GetUnmarshalClass(
LPMARSHAL iface, REFIID riid, void* pv, DWORD dwDestContext,
void* pvDestContext, DWORD mshlflags, CLSID* pCid)
{
MonikerMarshal *This = impl_from_IMarshal(iface);
TRACE("(%s, %p, %x, %p, %x, %p)\n", debugstr_guid(riid), pv,
dwDestContext, pvDestContext, mshlflags, pCid);
return IMoniker_GetClassID(This->moniker, pCid);
}
static HRESULT WINAPI MonikerMarshal_GetMarshalSizeMax(
LPMARSHAL iface, REFIID riid, void* pv, DWORD dwDestContext,
void* pvDestContext, DWORD mshlflags, DWORD* pSize)
{
MonikerMarshal *This = impl_from_IMarshal(iface);
HRESULT hr;
ULARGE_INTEGER size;
TRACE("(%s, %p, %x, %p, %x, %p)\n", debugstr_guid(riid), pv,
dwDestContext, pvDestContext, mshlflags, pSize);
hr = IMoniker_GetSizeMax(This->moniker, &size);
if (hr == S_OK)
*pSize = (DWORD)size.QuadPart;
return hr;
}
static HRESULT WINAPI MonikerMarshal_MarshalInterface(LPMARSHAL iface, IStream *pStm,
REFIID riid, void* pv, DWORD dwDestContext,
void* pvDestContext, DWORD mshlflags)
{
MonikerMarshal *This = impl_from_IMarshal(iface);
TRACE("(%p, %s, %p, %x, %p, %x)\n", pStm, debugstr_guid(riid), pv,
dwDestContext, pvDestContext, mshlflags);
return IMoniker_Save(This->moniker, pStm, FALSE);
}
static HRESULT WINAPI MonikerMarshal_UnmarshalInterface(LPMARSHAL iface, IStream *pStm, REFIID riid, void **ppv)
{
MonikerMarshal *This = impl_from_IMarshal(iface);
HRESULT hr;
TRACE("(%p, %s, %p)\n", pStm, debugstr_guid(riid), ppv);
hr = IMoniker_Load(This->moniker, pStm);
if (hr == S_OK)
hr = IMoniker_QueryInterface(This->moniker, riid, ppv);
return hr;
}
static HRESULT WINAPI MonikerMarshal_ReleaseMarshalData(LPMARSHAL iface, IStream *pStm)
{
TRACE("()\n");
/* can't release a state-based marshal as nothing on server side to
* release */
return S_OK;
}
static HRESULT WINAPI MonikerMarshal_DisconnectObject(LPMARSHAL iface, DWORD dwReserved)
{
TRACE("()\n");
/* can't disconnect a state-based marshal as nothing on server side to
* disconnect from */
return S_OK;
}
static const IMarshalVtbl VT_MonikerMarshal =
{
MonikerMarshal_QueryInterface,
MonikerMarshal_AddRef,
MonikerMarshal_Release,
MonikerMarshal_GetUnmarshalClass,
MonikerMarshal_GetMarshalSizeMax,
MonikerMarshal_MarshalInterface,
MonikerMarshal_UnmarshalInterface,
MonikerMarshal_ReleaseMarshalData,
MonikerMarshal_DisconnectObject
};
HRESULT MonikerMarshal_Create(IMoniker *inner, IUnknown **outer)
{
MonikerMarshal *This = HeapAlloc(GetProcessHeap(), 0, sizeof(*This));
if (!This) return E_OUTOFMEMORY;
This->lpVtbl = &VT_MonikerMarshalInner;
This->lpVtblMarshal = &VT_MonikerMarshal;
This->ref = 1;
This->moniker = inner;
*outer = (IUnknown *)&This->lpVtbl;
return S_OK;
}