Commit d1c14414 authored by Juergen Schmied's avatar Juergen Schmied Committed by Alexandre Julliard

- Moved 16 bit functions to a seperate file.

- First implementation for free threaded marshaller. - Fixed handling of REG_EXPAND_STRING registry values in CoCreateObject. - Fixed CoLoad/FreeLibrary functions. - Fixed use internal dll-list (used only for functions loading a dll internally without returning HMODULE).
parent c414344e
......@@ -21,12 +21,14 @@ C_SRCS = \
defaulthandler.c \
errorinfo.c \
filemoniker.c \
ftmarshal.c \
hglobalstream.c \
ifs.c \
itemmoniker.c \
marshal.c \
memlockbytes.c \
moniker.c \
ole16.c \
ole2.c \
ole2stubs.c \
ole2impl.c \
......@@ -45,4 +47,3 @@ RC_SRCS = ole32res.rc
@MAKE_DLL_RULES@
### Dependencies:
......@@ -45,89 +45,62 @@
#include "wine/obj_marshal.h"
#include "wine/obj_storage.h"
#include "wine/obj_channel.h"
#include "wine/winbase16.h"
#include "compobj_private.h"
#include "ifs.h"
#include "wine/debug.h"
WINE_DEFAULT_DEBUG_CHANNEL(ole);
/****************************************************************************
* COM External Lock structures and methods declaration
*
* This api provides a linked list to managed external references to
* COM objects.
* This section defines variables internal to the COM module.
*
* The public interface consists of three calls:
* COM_ExternalLockAddRef
* COM_ExternalLockRelease
* COM_ExternalLockFreeList
* TODO: Most of these things will have to be made thread-safe.
*/
HINSTANCE COMPOBJ_hInstance32 = 0;
#define EL_END_OF_LIST 0
#define EL_NOT_FOUND 0
static HRESULT COM_GetRegisteredClassObject(REFCLSID rclsid, DWORD dwClsContext, LPUNKNOWN* ppUnk);
static void COM_RevokeAllClasses();
static void COM_ExternalLockFreeList();
/*
* Declaration of the static structure that manage the
* external lock to COM objects.
/*****************************************************************************
* Appartment management stuff
*
* NOTE:
* per Thread values are stored in the TEB on offset 0xF80
*
* see www.microsoft.com/msj/1099/bugslayer/bugslayer1099.htm
*
*/
typedef struct COM_ExternalLock COM_ExternalLock;
typedef struct COM_ExternalLockList COM_ExternalLockList;
struct COM_ExternalLock
{
IUnknown *pUnk; /* IUnknown referenced */
ULONG uRefCount; /* external lock counter to IUnknown object*/
COM_ExternalLock *next; /* Pointer to next element in list */
};
typedef struct {
unsigned char threadingModell; // we use the COINIT flags
unsigned long threadID;
long AppartmentLockCount;
} OleAppartmentData;
struct COM_ExternalLockList
{
COM_ExternalLock *head; /* head of list */
};
typedef struct {
OleAppartmentData *AppartmentData;
} OleThreadData;
/* not jet used
static CRITICAL_SECTION csAppartmentData = CRITICAL_SECTION_INIT("csAppartmentData");
*/
/*
* Declaration and initialization of the static structure that manages
* the external lock to COM objects.
* the first STA created in a process is the main STA
*/
static COM_ExternalLockList elList = { EL_END_OF_LIST };
/*
* Public Interface to the external lock list
*/
static void COM_ExternalLockFreeList();
static void COM_ExternalLockAddRef(IUnknown *pUnk);
static void COM_ExternalLockRelease(IUnknown *pUnk, BOOL bRelAll);
void COM_ExternalLockDump(); /* testing purposes, not static to avoid warning */
/* not jet used
static OleAppartmentData * mainSTA;
*/
/*
* Private methods used to managed the linked list
* a Process can only have one MTA
*/
static BOOL COM_ExternalLockInsert(
IUnknown *pUnk);
static void COM_ExternalLockDelete(
COM_ExternalLock *element);
static COM_ExternalLock* COM_ExternalLockFind(
IUnknown *pUnk);
static COM_ExternalLock* COM_ExternalLockLocate(
COM_ExternalLock *element,
IUnknown *pUnk);
/****************************************************************************
* This section defines variables internal to the COM module.
*
* TODO: Most of these things will have to be made thread-safe.
*/
HINSTANCE16 COMPOBJ_hInstance = 0;
HINSTANCE COMPOBJ_hInstance32 = 0;
static int COMPOBJ_Attach = 0;
/* not jet used
static OleAppartmentData * processMTA;
*/
HTASK16 hETask = 0;
WORD Table_ETask[62];
/*
* This lock count counts the number of times CoInitialize is called. It is
......@@ -155,30 +128,30 @@ typedef struct tagRegisteredClass
struct tagRegisteredClass* nextClass;
} RegisteredClass;
static CRITICAL_SECTION csRegisteredClassList;
static CRITICAL_SECTION csRegisteredClassList = CRITICAL_SECTION_INIT("csRegisteredClassList");
static RegisteredClass* firstRegisteredClass = NULL;
/* this open DLL table belongs in a per process table, but my guess is that
* it shouldn't live in the kernel, so I'll put them out here in DLL
* space assuming that there is one OLE32 per process.
/*****************************************************************************
* This section contains OpenDllList definitions
*
* The OpenDllList contains only handles of dll loaded by CoGetClassObject or
* other functions what do LoadLibrary _without_ giving back a HMODULE.
* Without this list these handles would be freed never.
*
* FIXME: a DLL what says OK whenn asked for unloading is unloaded in the
* next unload-call but not before 600 sec.
*/
typedef struct tagOpenDll {
HINSTANCE hLibrary;
struct tagOpenDll *next;
} OpenDll;
static CRITICAL_SECTION csOpenDllList;
static CRITICAL_SECTION csOpenDllList = CRITICAL_SECTION_INIT("csOpenDllList");
static OpenDll *openDllList = NULL; /* linked list of open dlls */
/*****************************************************************************
* This section contains prototypes to internal methods for this
* module
*/
static HRESULT COM_GetRegisteredClassObject(REFCLSID rclsid,
DWORD dwClsContext,
LPUNKNOWN* ppUnk);
static void COM_RevokeAllClasses();
static void COMPOBJ_DLLList_Add(HANDLE hLibrary);
static void COMPOBJ_DllList_FreeUnused(int Timeout);
/******************************************************************************
......@@ -186,67 +159,98 @@ static void COM_RevokeAllClasses();
*/
void COMPOBJ_InitProcess( void )
{
InitializeCriticalSection( &csRegisteredClassList );
InitializeCriticalSection( &csOpenDllList );
}
void COMPOBJ_UninitProcess( void )
{
DeleteCriticalSection( &csRegisteredClassList );
DeleteCriticalSection( &csOpenDllList );
}
/******************************************************************************
* CoBuildVersion [COMPOBJ.1]
* CoBuildVersion [OLE32.4]
*
* RETURNS
* Current build version, hiword is majornumber, loword is minornumber
/*****************************************************************************
* This section contains OpenDllList implemantation
*/
DWORD WINAPI CoBuildVersion(void)
static void COMPOBJ_DLLList_Add(HANDLE hLibrary)
{
TRACE("Returning version %d, build %d.\n", rmm, rup);
return (rmm<<16)+rup;
}
OpenDll *ptr;
OpenDll *tmp;
LPMALLOC16 currentMalloc16=NULL;
TRACE("\n");
/***********************************************************************
* CoGetMalloc [COMPOBJ.4]
* RETURNS
* The current win16 IMalloc
*/
HRESULT WINAPI CoGetMalloc16(
DWORD dwMemContext, /* [in] unknown */
LPMALLOC16 * lpMalloc /* [out] current win16 malloc interface */
) {
if(!currentMalloc16)
currentMalloc16 = IMalloc16_Constructor();
*lpMalloc = currentMalloc16;
return S_OK;
EnterCriticalSection( &csOpenDllList );
if (openDllList == NULL) {
/* empty list -- add first node */
openDllList = (OpenDll*)HeapAlloc(GetProcessHeap(),0, sizeof(OpenDll));
openDllList->hLibrary=hLibrary;
openDllList->next = NULL;
} else {
/* search for this dll */
int found = FALSE;
for (ptr = openDllList; ptr->next != NULL; ptr=ptr->next) {
if (ptr->hLibrary == hLibrary) {
found = TRUE;
break;
}
}
if (!found) {
/* dll not found, add it */
tmp = openDllList;
openDllList = (OpenDll*)HeapAlloc(GetProcessHeap(),0, sizeof(OpenDll));
openDllList->hLibrary = hLibrary;
openDllList->next = tmp;
}
}
LeaveCriticalSection( &csOpenDllList );
}
/***********************************************************************
* CoCreateStandardMalloc [COMPOBJ.71]
*/
HRESULT WINAPI CoCreateStandardMalloc16(DWORD dwMemContext,
LPMALLOC16 *lpMalloc)
static void COMPOBJ_DllList_FreeUnused(int Timeout)
{
/* FIXME: docu says we shouldn't return the same allocator as in
* CoGetMalloc16 */
*lpMalloc = IMalloc16_Constructor();
return S_OK;
OpenDll *curr, *next, *prev = NULL;
typedef HRESULT(*DllCanUnloadNowFunc)(void);
DllCanUnloadNowFunc DllCanUnloadNow;
TRACE("\n");
EnterCriticalSection( &csOpenDllList );
for (curr = openDllList; curr != NULL; ) {
DllCanUnloadNow = (DllCanUnloadNowFunc) GetProcAddress(curr->hLibrary, "DllCanUnloadNow");
if ( (DllCanUnloadNow != NULL) && (DllCanUnloadNow() == S_OK) ) {
next = curr->next;
TRACE("freeing 0x%08x\n", curr->hLibrary);
FreeLibrary(curr->hLibrary);
HeapFree(GetProcessHeap(), 0, curr);
if (curr == openDllList) {
openDllList = next;
} else {
prev->next = next;
}
curr = next;
} else {
prev = curr;
curr = curr->next;
}
}
LeaveCriticalSection( &csOpenDllList );
}
/******************************************************************************
* CoInitialize [COMPOBJ.2]
* Set the win16 IMalloc used for memory management
* CoBuildVersion [COMPOBJ.1]
* CoBuildVersion [OLE32.4]
*
* RETURNS
* Current build version, hiword is majornumber, loword is minornumber
*/
HRESULT WINAPI CoInitialize16(
LPVOID lpReserved /* [in] pointer to win16 malloc interface */
) {
currentMalloc16 = (LPMALLOC16)lpReserved;
return S_OK;
DWORD WINAPI CoBuildVersion(void)
{
TRACE("Returning version %d, build %d.\n", rmm, rup);
return (rmm<<16)+rup;
}
/******************************************************************************
......@@ -334,18 +338,6 @@ HRESULT WINAPI CoInitializeEx(
}
/***********************************************************************
* CoUninitialize [COMPOBJ.3]
* Don't know what it does.
* 3-Nov-98 -- this was originally misspelled, I changed it to what I
* believe is the correct spelling
*/
void WINAPI CoUninitialize16(void)
{
TRACE("()\n");
CoFreeAllLibraries();
}
/***********************************************************************
* CoUninitialize [OLE32.47]
*
* This method will release the COM libraries.
......@@ -403,35 +395,32 @@ HRESULT WINAPI CoDisconnectObject( LPUNKNOWN lpUnk, DWORD reserved )
return S_OK;
}
/***********************************************************************
* IsEqualGUID [COMPOBJ.18]
*
* Compares two Unique Identifiers.
/******************************************************************************
* CoCreateGuid[OLE32.6]
*
* RETURNS
* TRUE if equal
*/
BOOL16 WINAPI IsEqualGUID16(
GUID* g1, /* [in] unique id 1 */
GUID* g2 /* [in] unique id 2 */
HRESULT WINAPI CoCreateGuid(
GUID *pguid /* [out] points to the GUID to initialize */
) {
return !memcmp( g1, g2, sizeof(GUID) );
return UuidCreate(pguid);
}
/******************************************************************************
* CLSIDFromString [COMPOBJ.20]
* CLSIDFromString [OLE32.3]
* IIDFromString [OLE32.74]
* Converts a unique identifier from its string representation into
* the GUID struct.
*
* Class id: DWORD-WORD-WORD-BYTES[2]-BYTES[6]
* UNDOCUMENTED
* If idstr is not a valid CLSID string then it gets treated as a ProgID
*
* RETURNS
* the converted GUID
*/
HRESULT WINAPI CLSIDFromString16(
LPCOLESTR16 idstr, /* [in] string representation of guid */
CLSID *id /* [out] GUID converted from string */
) {
HRESULT WINAPI __CLSIDFromStringA(
LPCSTR idstr, /* [in] string representation of guid */
CLSID *id) /* [out] GUID converted from string */
{
BYTE *s = (BYTE *) idstr;
int i;
BYTE table[256];
......@@ -446,13 +435,11 @@ HRESULT WINAPI CLSIDFromString16(
if ((s[0]!='{') || (s[9]!='-') || (s[14]!='-') || (s[19]!='-') || (s[24]!='-') || (s[37]!='}'))
return CO_E_CLASSSTRING;
for (i=1; i<37; i++)
{
for (i=1; i<37; i++) {
if ((i == 9)||(i == 14)||(i == 19)||(i == 24)) continue;
if (!(((s[i] >= '0') && (s[i] <= '9')) ||
((s[i] >= 'a') && (s[i] <= 'f')) ||
((s[i] >= 'A') && (s[i] <= 'F')))
)
((s[i] >= 'A') && (s[i] <= 'F'))))
return CO_E_CLASSSTRING;
}
}
......@@ -490,28 +477,6 @@ HRESULT WINAPI CLSIDFromString16(
return S_OK;
}
/******************************************************************************
* CoCreateGuid[OLE32.6]
*
*/
HRESULT WINAPI CoCreateGuid(
GUID *pguid /* [out] points to the GUID to initialize */
) {
return UuidCreate(pguid);
}
/******************************************************************************
* CLSIDFromString [OLE32.3]
* IIDFromString [OLE32.74]
* Converts a unique identifier from its string representation into
* the GUID struct.
*
* UNDOCUMENTED
* If idstr is not a valid CLSID string then it gets treated as a ProgID
*
* RETURNS
* the converted GUID
*/
HRESULT WINAPI CLSIDFromString(
LPCOLESTR idstr, /* [in] string representation of GUID */
CLSID *id ) /* [out] GUID represented by above string */
......@@ -521,7 +486,9 @@ HRESULT WINAPI CLSIDFromString(
if (!WideCharToMultiByte( CP_ACP, 0, idstr, -1, xid, sizeof(xid), NULL, NULL ))
return CO_E_CLASSSTRING;
ret = CLSIDFromString16(xid,id);
ret = __CLSIDFromStringA(xid,id);
if(ret != S_OK) { /* It appears a ProgID is also valid */
ret = CLSIDFromProgID(idstr, id);
}
......@@ -570,66 +537,6 @@ HRESULT WINE_StringFromCLSID(
return S_OK;
}
extern BOOL WINAPI K32WOWCallback16Ex( DWORD vpfn16, DWORD dwFlags,
DWORD cbArgs, LPVOID pArgs,
LPDWORD pdwRetCode );
/******************************************************************************
* _xmalloc16 [internal]
* Allocates size bytes from the standard ole16 allocator.
*
* RETURNS
* the allocated segmented pointer and a HRESULT
*/
HRESULT
_xmalloc16(DWORD size, SEGPTR *ptr) {
LPMALLOC16 mllc;
DWORD args[2];
if (CoGetMalloc16(0,&mllc))
return E_OUTOFMEMORY;
args[0] = (DWORD)mllc;
args[1] = size;
/* No need for a Callback entry, we have WOWCallback16Ex which does
* everything we need.
*/
if (!K32WOWCallback16Ex(
(DWORD)((ICOM_VTABLE(IMalloc16)*)MapSL(
(SEGPTR)ICOM_VTBL(((LPMALLOC16)MapSL((SEGPTR)mllc))))
)->Alloc,
WCB16_CDECL,
2*sizeof(DWORD),
(LPVOID)args,
(LPDWORD)ptr
)) {
ERR("CallTo16 IMalloc16 (%ld) failed\n",size);
return E_FAIL;
}
return S_OK;
}
/******************************************************************************
* StringFromCLSID [COMPOBJ.19]
* Converts a GUID into the respective string representation.
* The target string is allocated using the OLE IMalloc.
*
* RETURNS
* the string representation and HRESULT
*/
HRESULT WINAPI StringFromCLSID16(
REFCLSID id, /* [in] the GUID to be converted */
LPOLESTR16 *idstr /* [out] a pointer to a to-be-allocated segmented pointer pointing to the resulting string */
) {
HRESULT ret;
ret = _xmalloc16(40,(SEGPTR*)idstr);
if (ret != S_OK)
return ret;
return WINE_StringFromCLSID(id,MapSL((SEGPTR)*idstr));
}
/******************************************************************************
* StringFromCLSID [OLE32.151]
......@@ -733,114 +640,38 @@ HRESULT WINAPI ProgIDFromCLSID(
}
/******************************************************************************
* ProgIDFromCLSID [COMPOBJ.62]
* Converts a class id into the respective Program ID. (By using a registry lookup)
* RETURNS S_OK on success
* riid associated with the progid
* CLSIDFromProgID [OLE32.2]
* Converts a program id into the respective GUID. (By using a registry lookup)
* RETURNS
* riid associated with the progid
*/
HRESULT WINAPI ProgIDFromCLSID16(
REFCLSID clsid, /* [in] class id as found in registry */
LPOLESTR16 *lplpszProgID/* [out] associated Prog ID */
) {
char strCLSID[50], *buf, *buf2;
DWORD buf2len;
HKEY xhkey;
HRESULT ret = S_OK;
HRESULT WINAPI CLSIDFromProgID(
LPCOLESTR progid, /* [in] program id as found in registry */
LPCLSID riid ) /* [out] associated CLSID */
{
static const WCHAR clsidW[] = { '\\','C','L','S','I','D',0 };
char buf2[80];
DWORD buf2len = sizeof(buf2);
HKEY xhkey;
WINE_StringFromCLSID(clsid, strCLSID);
WCHAR *buf = HeapAlloc( GetProcessHeap(),0,(strlenW(progid)+8) * sizeof(WCHAR) );
strcpyW( buf, progid );
strcatW( buf, clsidW );
if (RegOpenKeyW(HKEY_CLASSES_ROOT,buf,&xhkey))
{
HeapFree(GetProcessHeap(),0,buf);
return CO_E_CLASSSTRING;
}
HeapFree(GetProcessHeap(),0,buf);
buf = HeapAlloc(GetProcessHeap(), 0, strlen(strCLSID)+14);
sprintf(buf,"CLSID\\%s\\ProgID", strCLSID);
if (RegOpenKeyA(HKEY_CLASSES_ROOT, buf, &xhkey))
ret = REGDB_E_CLASSNOTREG;
HeapFree(GetProcessHeap(), 0, buf);
if (ret == S_OK)
{
buf2 = HeapAlloc(GetProcessHeap(), 0, 255);
buf2len = 255;
if (RegQueryValueA(xhkey, NULL, buf2, &buf2len))
ret = REGDB_E_CLASSNOTREG;
if (ret == S_OK)
{
ret = _xmalloc16(buf2len+1, (SEGPTR*)lplpszProgID);
if (ret != S_OK)
return ret;
strcpy(MapSL((SEGPTR)*lplpszProgID),buf2);
ret = S_OK;
}
HeapFree(GetProcessHeap(), 0, buf2);
}
RegCloseKey(xhkey);
return ret;
}
/******************************************************************************
* CLSIDFromProgID [COMPOBJ.61]
* Converts a program id into the respective GUID. (By using a registry lookup)
* RETURNS
* riid associated with the progid
*/
HRESULT WINAPI CLSIDFromProgID16(
LPCOLESTR16 progid, /* [in] program id as found in registry */
LPCLSID riid /* [out] associated CLSID */
) {
char *buf,buf2[80];
DWORD buf2len;
HRESULT err;
HKEY xhkey;
buf = HeapAlloc(GetProcessHeap(),0,strlen(progid)+8);
sprintf(buf,"%s\\CLSID",progid);
if ((err=RegOpenKeyA(HKEY_CLASSES_ROOT,buf,&xhkey))) {
HeapFree(GetProcessHeap(),0,buf);
return CO_E_CLASSSTRING;
}
HeapFree(GetProcessHeap(),0,buf);
buf2len = sizeof(buf2);
if ((err=RegQueryValueA(xhkey,NULL,buf2,&buf2len))) {
RegCloseKey(xhkey);
return CO_E_CLASSSTRING;
}
RegCloseKey(xhkey);
return CLSIDFromString16(buf2,riid);
}
/******************************************************************************
* CLSIDFromProgID [OLE32.2]
* Converts a program id into the respective GUID. (By using a registry lookup)
* RETURNS
* riid associated with the progid
*/
HRESULT WINAPI CLSIDFromProgID(
LPCOLESTR progid, /* [in] program id as found in registry */
LPCLSID riid ) /* [out] associated CLSID */
{
static const WCHAR clsidW[] = { '\\','C','L','S','I','D',0 };
char buf2[80];
DWORD buf2len = sizeof(buf2);
HKEY xhkey;
WCHAR *buf = HeapAlloc( GetProcessHeap(),0,(strlenW(progid)+8) * sizeof(WCHAR) );
strcpyW( buf, progid );
strcatW( buf, clsidW );
if (RegOpenKeyW(HKEY_CLASSES_ROOT,buf,&xhkey))
{
HeapFree(GetProcessHeap(),0,buf);
return CO_E_CLASSSTRING;
}
HeapFree(GetProcessHeap(),0,buf);
if (RegQueryValueA(xhkey,NULL,buf2,&buf2len))
{
RegCloseKey(xhkey);
return CO_E_CLASSSTRING;
}
RegCloseKey(xhkey);
return CLSIDFromString16(buf2,riid);
}
if (RegQueryValueA(xhkey,NULL,buf2,&buf2len))
{
RegCloseKey(xhkey);
return CO_E_CLASSSTRING;
}
RegCloseKey(xhkey);
return __CLSIDFromStringA(buf2,riid);
}
......@@ -900,8 +731,7 @@ HRESULT WINAPI CoGetPSClsid(
/* We have the CLSid we want back from the registry as a string, so
lets convert it into a CLSID structure */
if ( (CLSIDFromString16(buf2,pclsid)) != NOERROR)
{
if ( (__CLSIDFromStringA(buf2,pclsid)) != NOERROR) {
return E_INVALIDARG;
}
......@@ -952,85 +782,6 @@ HRESULT WINAPI ReadClassStm(IStream *pStm,CLSID *pclsid)
return S_OK;
}
/* FIXME: this function is not declared in the WINELIB headers. But where should it go ? */
/***********************************************************************
* LookupETask (COMPOBJ.94)
*/
HRESULT WINAPI LookupETask16(HTASK16 *hTask,LPVOID p) {
FIXME("(%p,%p),stub!\n",hTask,p);
if ((*hTask = GetCurrentTask()) == hETask) {
memcpy(p, Table_ETask, sizeof(Table_ETask));
}
return 0;
}
/* FIXME: this function is not declared in the WINELIB headers. But where should it go ? */
/***********************************************************************
* SetETask (COMPOBJ.95)
*/
HRESULT WINAPI SetETask16(HTASK16 hTask, LPVOID p) {
FIXME("(%04x,%p),stub!\n",hTask,p);
hETask = hTask;
return 0;
}
/* FIXME: this function is not declared in the WINELIB headers. But where should it go ? */
/***********************************************************************
* CALLOBJECTINWOW (COMPOBJ.201)
*/
HRESULT WINAPI CallObjectInWOW(LPVOID p1,LPVOID p2) {
FIXME("(%p,%p),stub!\n",p1,p2);
return 0;
}
/******************************************************************************
* CoRegisterClassObject [COMPOBJ.5]
*
* Don't know where it registers it ...
*/
HRESULT WINAPI CoRegisterClassObject16(
REFCLSID rclsid,
LPUNKNOWN pUnk,
DWORD dwClsContext, /* [in] CLSCTX flags indicating the context in which to run the executable */
DWORD flags, /* [in] REGCLS flags indicating how connections are made */
LPDWORD lpdwRegister
) {
char buf[80];
WINE_StringFromCLSID(rclsid,buf);
FIXME("(%s,%p,0x%08lx,0x%08lx,%p),stub\n",
buf,pUnk,dwClsContext,flags,lpdwRegister
);
return 0;
}
/******************************************************************************
* CoRevokeClassObject [COMPOBJ.6]
*
*/
HRESULT WINAPI CoRevokeClassObject16(DWORD dwRegister) /* [in] token on class obj */
{
FIXME("(0x%08lx),stub!\n", dwRegister);
return 0;
}
/******************************************************************************
* CoFileTimeToDosDateTime [COMPOBJ.30]
*/
BOOL16 WINAPI CoFileTimeToDosDateTime16(const FILETIME *ft, LPWORD lpDosDate, LPWORD lpDosTime)
{
return FileTimeToDosDateTime(ft, lpDosDate, lpDosTime);
}
/******************************************************************************
* CoDosDateTimeToFileTime [COMPOBJ.31]
*/
BOOL16 WINAPI CoDosDateTimeToFileTime16(WORD wDosDate, WORD wDosTime, FILETIME *ft)
{
return DosDateTimeToFileTime(wDosDate, wDosTime, ft);
}
/***
* COM_GetRegisteredClassObject
......@@ -1319,6 +1070,32 @@ end:
}
/***********************************************************************
* compobj_RegReadPath [internal]
*
* Reads a registry value and expands it when nessesary
*/
HRESULT compobj_RegReadPath(char * keyname, char * valuename, char * dst, int dstlen)
{
HRESULT hres;
HKEY key;
DWORD keytype;
char src[MAX_PATH];
DWORD dwLength = dstlen;
if((hres = RegOpenKeyExA(HKEY_CLASSES_ROOT, keyname, 0, KEY_READ, &key)) == ERROR_SUCCESS) {
if( (hres = RegQueryValueExA(key, NULL, NULL, &keytype, (LPBYTE)src, &dwLength)) == ERROR_SUCCESS ) {
if (keytype == REG_EXPAND_SZ) {
if (dstlen <= ExpandEnvironmentStringsA(src, dst, dstlen)) hres = ERROR_MORE_DATA;
} else {
strncpy(dst, src, dstlen);
}
}
RegCloseKey (key);
}
return hres;
}
/***********************************************************************
* CoGetClassObject [COMPOBJ.7]
* CoGetClassObject [OLE32.16]
*
......@@ -1334,19 +1111,13 @@ HRESULT WINAPI CoGetClassObject(
LPUNKNOWN regClassObject;
HRESULT hres = E_UNEXPECTED;
char xclsid[80];
WCHAR ProviderName[MAX_PATH+1];
DWORD ProviderNameLen = sizeof(ProviderName);
HINSTANCE hLibrary;
typedef HRESULT (CALLBACK *DllGetClassObjectFunc)(REFCLSID clsid,
REFIID iid, LPVOID *ppv);
typedef HRESULT (CALLBACK *DllGetClassObjectFunc)(REFCLSID clsid, REFIID iid, LPVOID *ppv);
DllGetClassObjectFunc DllGetClassObject;
WINE_StringFromCLSID((LPCLSID)rclsid,xclsid);
TRACE("\n\tCLSID:\t%s,\n\tIID:\t%s\n",
debugstr_guid(rclsid),
debugstr_guid(iid)
);
TRACE("\n\tCLSID:\t%s,\n\tIID:\t%s\n", debugstr_guid(rclsid), debugstr_guid(iid));
if (pServerInfo) {
FIXME("\tpServerInfo: name=%s\n",debugstr_w(pServerInfo->pwszName));
......@@ -1374,41 +1145,35 @@ HRESULT WINAPI CoGetClassObject(
return hres;
}
if ((CLSCTX_INPROC_SERVER|CLSCTX_INPROC_HANDLER) & dwClsContext) {
HKEY key;
char buf[200];
memset(ProviderName,0,sizeof(ProviderName));
sprintf(buf,"CLSID\\%s\\InprocServer32",xclsid);
if (((hres = RegOpenKeyExA(HKEY_CLASSES_ROOT, buf, 0, KEY_READ, &key)) != ERROR_SUCCESS) ||
((hres = RegQueryValueExW(key,NULL,NULL,NULL,(LPBYTE)ProviderName,&ProviderNameLen)),
RegCloseKey (key),
hres != ERROR_SUCCESS))
{
/* first try: in-process */
if ((CLSCTX_INPROC_SERVER | CLSCTX_INPROC_HANDLER) & dwClsContext) {
char keyname[MAX_PATH];
char dllpath[MAX_PATH+1];
sprintf(keyname,"CLSID\\%s\\InprocServer32",xclsid);
if ( compobj_RegReadPath(keyname, NULL, dllpath, sizeof(dllpath)) != ERROR_SUCCESS) {
/* failure: CLSID is not found in registry */
WARN("class %s not registred\n", xclsid);
hres = REGDB_E_CLASSNOTREG;
}
/* Don't ask me. MSDN says that CoGetClassObject does NOT call CoLoadLibrary */
else if ((hLibrary = CoLoadLibrary(ProviderName, TRUE)) == 0)
{
FIXME("couldn't load InprocServer32 dll %s\n", debugstr_w(ProviderName));
hres = E_ACCESSDENIED; /* or should this be CO_E_DLLNOTFOUND? */
}
else if (!(DllGetClassObject = (DllGetClassObjectFunc)GetProcAddress(hLibrary, "DllGetClassObject")))
{
/* not sure if this should be called here CoFreeLibrary(hLibrary);*/
FIXME("couldn't find function DllGetClassObject in %s\n", debugstr_w(ProviderName));
hres = E_ACCESSDENIED;
}
else
{
/* Ask the DLL for its class object. (there was a note here about
* class factories but this is good.
*/
} else {
if ((hLibrary = LoadLibraryExA(dllpath, 0, LOAD_WITH_ALTERED_SEARCH_PATH)) == 0) {
/* failure: DLL could not be loaded */
ERR("couldn't load InprocServer32 dll %s\n", dllpath);
hres = E_ACCESSDENIED; /* FIXME: or should this be CO_E_DLLNOTFOUND? */
} else if (!(DllGetClassObject = (DllGetClassObjectFunc)GetProcAddress(hLibrary, "DllGetClassObject"))) {
/* failure: the dll did not export DllGetClassObject */
ERR("couldn't find function DllGetClassObject in %s\n", dllpath);
FreeLibrary( hLibrary );
hres = CO_E_DLLNOTFOUND;
} else {
/* OK: get the ClassObject */
COMPOBJ_DLLList_Add( hLibrary );
return DllGetClassObject(rclsid, iid, ppv);
}
}
}
}
/* Next try out of process */
if (CLSCTX_LOCAL_SERVER & dwClsContext)
{
......@@ -1525,17 +1290,6 @@ HRESULT WINAPI GetClassFile(LPCOLESTR filePathName,CLSID *pclsid)
return MK_E_INVALIDEXTENSION;
}
/******************************************************************************
* CoRegisterMessageFilter [COMPOBJ.27]
*/
HRESULT WINAPI CoRegisterMessageFilter16(
LPMESSAGEFILTER lpMessageFilter,
LPMESSAGEFILTER *lplpMessageFilter
) {
FIXME("(%p,%p),stub!\n",lpMessageFilter,lplpMessageFilter);
return 0;
}
/***********************************************************************
* CoCreateInstance [COMPOBJ.13]
* CoCreateInstance [OLE32.7]
......@@ -1662,93 +1416,47 @@ HRESULT WINAPI CoCreateInstanceEx(
}
/***********************************************************************
* CoFreeLibrary [OLE32.13]
* CoLoadLibrary (OLE32.30)
*/
void WINAPI CoFreeLibrary(HINSTANCE hLibrary)
HINSTANCE WINAPI CoLoadLibrary(LPOLESTR lpszLibName, BOOL bAutoFree)
{
OpenDll *ptr, *prev;
OpenDll *tmp;
EnterCriticalSection( &csOpenDllList );
TRACE("(%s, %d)\n", debugstr_w(lpszLibName), bAutoFree);
/* lookup library in linked list */
prev = NULL;
for (ptr = openDllList; ptr != NULL; ptr=ptr->next) {
if (ptr->hLibrary == hLibrary) {
break;
}
prev = ptr;
}
return LoadLibraryExW(lpszLibName, 0, LOAD_WITH_ALTERED_SEARCH_PATH);
}
if (ptr == NULL) {
/* shouldn't happen if user passed in a valid hLibrary */
goto end;
}
/* assert: ptr points to the library entry to free */
/* free library and remove node from list */
FreeLibrary(hLibrary);
if (ptr == openDllList) {
tmp = openDllList->next;
HeapFree(GetProcessHeap(), 0, openDllList);
openDllList = tmp;
} else {
tmp = ptr->next;
HeapFree(GetProcessHeap(), 0, ptr);
prev->next = tmp;
}
end:
LeaveCriticalSection( &csOpenDllList );
/***********************************************************************
* CoFreeLibrary [OLE32.13]
*
* NOTES: don't belive the docu
*/
void WINAPI CoFreeLibrary(HINSTANCE hLibrary)
{
FreeLibrary(hLibrary);
}
/***********************************************************************
* CoFreeAllLibraries [OLE32.12]
*
* NOTES: don't belive the docu
*/
void WINAPI CoFreeAllLibraries(void)
{
OpenDll *ptr, *tmp;
EnterCriticalSection( &csOpenDllList );
for (ptr = openDllList; ptr != NULL; ) {
tmp=ptr->next;
CoFreeLibrary(ptr->hLibrary);
ptr = tmp;
}
LeaveCriticalSection( &csOpenDllList );
/* NOP */
}
/***********************************************************************
* CoFreeUnusedLibraries [COMPOBJ.17]
* CoFreeUnusedLibraries [OLE32.14]
*
* FIXME: Calls to CoFreeUnusedLibraries from any thread always route
* through the main apartment's thread to call DllCanUnloadNow
*/
void WINAPI CoFreeUnusedLibraries(void)
{
OpenDll *ptr, *tmp;
typedef HRESULT(*DllCanUnloadNowFunc)(void);
DllCanUnloadNowFunc DllCanUnloadNow;
EnterCriticalSection( &csOpenDllList );
for (ptr = openDllList; ptr != NULL; ) {
DllCanUnloadNow = (DllCanUnloadNowFunc)
GetProcAddress(ptr->hLibrary, "DllCanUnloadNow");
if ( (DllCanUnloadNow != NULL) &&
(DllCanUnloadNow() == S_OK) ) {
tmp=ptr->next;
CoFreeLibrary(ptr->hLibrary);
ptr = tmp;
} else {
ptr=ptr->next;
}
}
LeaveCriticalSection( &csOpenDllList );
COMPOBJ_DllList_FreeUnused(0);
}
/***********************************************************************
......@@ -1767,157 +1475,149 @@ HRESULT WINAPI CoFileTimeNow( FILETIME *lpFileTime ) /* [out] the current time *
/***********************************************************************
* CoLoadLibrary (OLE32.30)
*/
HINSTANCE WINAPI CoLoadLibrary(LPOLESTR lpszLibName, BOOL bAutoFree)
static void COM_RevokeAllClasses()
{
HINSTANCE hLibrary;
OpenDll *ptr;
OpenDll *tmp;
EnterCriticalSection( &csRegisteredClassList );
TRACE("(%s, %d)\n", debugstr_w(lpszLibName), bAutoFree);
while (firstRegisteredClass!=0)
{
CoRevokeClassObject(firstRegisteredClass->dwCookie);
}
hLibrary = LoadLibraryExW(lpszLibName, 0, LOAD_WITH_ALTERED_SEARCH_PATH);
LeaveCriticalSection( &csRegisteredClassList );
}
if (!bAutoFree)
return hLibrary;
/****************************************************************************
* COM External Lock methods implementation
*
* This api provides a linked list to managed external references to
* COM objects.
*
* The public interface consists of three calls:
* COM_ExternalLockAddRef
* COM_ExternalLockRelease
* COM_ExternalLockFreeList
*/
EnterCriticalSection( &csOpenDllList );
#define EL_END_OF_LIST 0
#define EL_NOT_FOUND 0
if (openDllList == NULL) {
/* empty list -- add first node */
openDllList = (OpenDll*)HeapAlloc(GetProcessHeap(),0, sizeof(OpenDll));
openDllList->hLibrary=hLibrary;
openDllList->next = NULL;
} else {
/* search for this dll */
int found = FALSE;
for (ptr = openDllList; ptr->next != NULL; ptr=ptr->next) {
if (ptr->hLibrary == hLibrary) {
found = TRUE;
break;
}
}
if (!found) {
/* dll not found, add it */
tmp = openDllList;
openDllList = (OpenDll*)HeapAlloc(GetProcessHeap(),0, sizeof(OpenDll));
openDllList->hLibrary = hLibrary;
openDllList->next = tmp;
}
}
/*
* Declaration of the static structure that manage the
* external lock to COM objects.
*/
typedef struct COM_ExternalLock COM_ExternalLock;
typedef struct COM_ExternalLockList COM_ExternalLockList;
LeaveCriticalSection( &csOpenDllList );
struct COM_ExternalLock
{
IUnknown *pUnk; /* IUnknown referenced */
ULONG uRefCount; /* external lock counter to IUnknown object*/
COM_ExternalLock *next; /* Pointer to next element in list */
};
return hLibrary;
}
struct COM_ExternalLockList
{
COM_ExternalLock *head; /* head of list */
};
/***********************************************************************
* CoInitializeWOW (OLE32.27)
/*
* Declaration and initialization of the static structure that manages
* the external lock to COM objects.
*/
HRESULT WINAPI CoInitializeWOW(DWORD x,DWORD y) {
FIXME("(0x%08lx,0x%08lx),stub!\n",x,y);
return 0;
}
static COM_ExternalLockList elList = { EL_END_OF_LIST };
/******************************************************************************
* CoLockObjectExternal [COMPOBJ.63]
/*
* Private methods used to managed the linked list
*/
HRESULT WINAPI CoLockObjectExternal16(
LPUNKNOWN pUnk, /* [in] object to be locked */
BOOL16 fLock, /* [in] do lock */
BOOL16 fLastUnlockReleases /* [in] ? */
) {
FIXME("(%p,%d,%d),stub!\n",pUnk,fLock,fLastUnlockReleases);
return S_OK;
}
/******************************************************************************
* CoLockObjectExternal [OLE32.31]
static COM_ExternalLock* COM_ExternalLockLocate(
COM_ExternalLock *element,
IUnknown *pUnk);
/****************************************************************************
* Internal - Insert a new IUnknown* to the linked list
*/
HRESULT WINAPI CoLockObjectExternal(
LPUNKNOWN pUnk, /* [in] object to be locked */
BOOL fLock, /* [in] do lock */
BOOL fLastUnlockReleases) /* [in] unlock all */
static BOOL COM_ExternalLockInsert(
IUnknown *pUnk)
{
COM_ExternalLock *newLock = NULL;
COM_ExternalLock *previousHead = NULL;
if (fLock)
{
/*
* Increment the external lock coutner, COM_ExternalLockAddRef also
* increment the object's internal lock counter.
*/
COM_ExternalLockAddRef( pUnk);
}
else
{
/*
* Decrement the external lock coutner, COM_ExternalLockRelease also
* decrement the object's internal lock counter.
*/
COM_ExternalLockRelease( pUnk, fLastUnlockReleases);
}
/*
* Allocate space for the new storage object
*/
newLock = HeapAlloc(GetProcessHeap(), 0, sizeof(COM_ExternalLock));
return S_OK;
}
if (newLock!=NULL) {
if ( elList.head == EL_END_OF_LIST ) {
elList.head = newLock; /* The list is empty */
} else {
/* insert does it at the head */
previousHead = elList.head;
elList.head = newLock;
}
/***********************************************************************
* CoGetState [COMPOBJ.115]
*/
HRESULT WINAPI CoGetState16(LPDWORD state)
{
FIXME("(%p),stub!\n", state);
*state = 0;
return S_OK;
}
/***********************************************************************
* CoSetState [OLE32.42]
*/
HRESULT WINAPI CoSetState(LPDWORD state)
{
FIXME("(%p),stub!\n", state);
if (state) *state = 0;
return S_OK;
}
/***********************************************************************
* CoCreateFreeThreadedMarshaler [OLE32.5]
*/
HRESULT WINAPI CoCreateFreeThreadedMarshaler (LPUNKNOWN punkOuter, LPUNKNOWN* ppunkMarshal)
{
FIXME ("(%p %p): stub\n", punkOuter, ppunkMarshal);
/* Set new list item data member */
newLock->pUnk = pUnk;
newLock->uRefCount = 1;
newLock->next = previousHead;
return S_OK;
return TRUE;
}
return FALSE;
}
/***
* COM_RevokeAllClasses
*
* This method is called when the COM libraries are uninitialized to
* release all the references to the class objects registered with
* the library
/****************************************************************************
* Internal - Method that removes an item from the linked list.
*/
static void COM_RevokeAllClasses()
static void COM_ExternalLockDelete(
COM_ExternalLock *itemList)
{
EnterCriticalSection( &csRegisteredClassList );
COM_ExternalLock *current = elList.head;
while (firstRegisteredClass!=0)
{
CoRevokeClassObject(firstRegisteredClass->dwCookie);
}
if ( current == itemList ) {
/* this section handles the deletion of the first node */
elList.head = itemList->next;
HeapFree( GetProcessHeap(), 0, itemList);
} else {
do {
if ( current->next == itemList ){ /* We found the item to free */
current->next = itemList->next; /* readjust the list pointers */
HeapFree( GetProcessHeap(), 0, itemList);
break;
}
LeaveCriticalSection( &csRegisteredClassList );
/* Skip to the next item */
current = current->next;
} while ( current != EL_END_OF_LIST );
}
}
/****************************************************************************
* COM External Lock methods implementation
* Internal - Recursivity agent for IUnknownExternalLockList_Find
*
* NOTES: how long can the list be ?? (recursive!!!)
*/
static COM_ExternalLock* COM_ExternalLockLocate( COM_ExternalLock *element, IUnknown *pUnk)
{
if ( element == EL_END_OF_LIST )
return EL_NOT_FOUND;
else if ( element->pUnk == pUnk ) /* We found it */
return element;
else /* Not the right guy, keep on looking */
return COM_ExternalLockLocate( element->next, pUnk);
}
/****************************************************************************
* Public - Method that increments the count for a IUnknown* in the linked
* list. The item is inserted if not already in the list.
*/
static void COM_ExternalLockAddRef(
IUnknown *pUnk)
static void COM_ExternalLockAddRef(IUnknown *pUnk)
{
COM_ExternalLock *externalLock = COM_ExternalLockFind(pUnk);
COM_ExternalLock *externalLock = COM_ExternalLockLocate(elList.head, pUnk);
/*
* Add an external lock to the object. If it was already externally
......@@ -1944,17 +1644,14 @@ static void COM_ExternalLockRelease(
IUnknown *pUnk,
BOOL bRelAll)
{
COM_ExternalLock *externalLock = COM_ExternalLockFind(pUnk);
COM_ExternalLock *externalLock = COM_ExternalLockLocate(elList.head, pUnk);
if ( externalLock != EL_NOT_FOUND )
{
do
{
if ( externalLock != EL_NOT_FOUND ) {
do {
externalLock->uRefCount--; /* release external locks */
IUnknown_Release(pUnk); /* release local locks as well */
if ( bRelAll == FALSE )
break; /* perform single release */
if ( bRelAll == FALSE ) break; /* perform single release */
} while ( externalLock->uRefCount > 0 );
......@@ -1970,10 +1667,8 @@ static void COM_ExternalLockFreeList()
COM_ExternalLock *head;
head = elList.head; /* grab it by the head */
while ( head != EL_END_OF_LIST )
{
while ( head != EL_END_OF_LIST ) {
COM_ExternalLockDelete(head); /* get rid of the head stuff */
head = elList.head; /* get the new head... */
}
}
......@@ -1987,144 +1682,98 @@ void COM_ExternalLockDump()
DPRINTF("\nExternal lock list contains:\n");
while ( current != EL_END_OF_LIST )
{
DPRINTF( "\t%p with %lu references count.\n", current->pUnk, current->uRefCount);
while ( current != EL_END_OF_LIST ) {
DPRINTF( "\t%p with %lu references count.\n", current->pUnk, current->uRefCount);
/* Skip to the next item */
current = current->next;
}
}
/****************************************************************************
* Internal - Find a IUnknown* in the linked list
*/
static COM_ExternalLock* COM_ExternalLockFind(
IUnknown *pUnk)
{
return COM_ExternalLockLocate(elList.head, pUnk);
}
/****************************************************************************
* Internal - Recursivity agent for IUnknownExternalLockList_Find
/******************************************************************************
* CoLockObjectExternal [OLE32.31]
*/
static COM_ExternalLock* COM_ExternalLockLocate(
COM_ExternalLock *element,
IUnknown *pUnk)
HRESULT WINAPI CoLockObjectExternal(
LPUNKNOWN pUnk, /* [in] object to be locked */
BOOL fLock, /* [in] do lock */
BOOL fLastUnlockReleases) /* [in] unlock all */
{
if ( element == EL_END_OF_LIST )
return EL_NOT_FOUND;
else if ( element->pUnk == pUnk ) /* We found it */
return element;
if (fLock) {
/*
* Increment the external lock coutner, COM_ExternalLockAddRef also
* increment the object's internal lock counter.
*/
COM_ExternalLockAddRef( pUnk);
} else {
/*
* Decrement the external lock coutner, COM_ExternalLockRelease also
* decrement the object's internal lock counter.
*/
COM_ExternalLockRelease( pUnk, fLastUnlockReleases);
}
else /* Not the right guy, keep on looking */
return COM_ExternalLockLocate( element->next, pUnk);
return S_OK;
}
/****************************************************************************
* Internal - Insert a new IUnknown* to the linked list
/***********************************************************************
* CoInitializeWOW (OLE32.27)
*/
static BOOL COM_ExternalLockInsert(
IUnknown *pUnk)
{
COM_ExternalLock *newLock = NULL;
COM_ExternalLock *previousHead = NULL;
/*
* Allocate space for the new storage object
*/
newLock = HeapAlloc(GetProcessHeap(), 0, sizeof(COM_ExternalLock));
if (newLock!=NULL)
{
if ( elList.head == EL_END_OF_LIST )
{
elList.head = newLock; /* The list is empty */
}
else
{
/*
* insert does it at the head
*/
previousHead = elList.head;
elList.head = newLock;
}
/*
* Set new list item data member
*/
newLock->pUnk = pUnk;
newLock->uRefCount = 1;
newLock->next = previousHead;
return TRUE;
}
else
return FALSE;
HRESULT WINAPI CoInitializeWOW(DWORD x,DWORD y) {
FIXME("(0x%08lx,0x%08lx),stub!\n",x,y);
return 0;
}
/****************************************************************************
* Internal - Method that removes an item from the linked list.
static IUnknown * pUnkState = 0; /* FIXME: thread local */
static int nStatCounter = 0; /* global */
static HMODULE hOleAut32 = 0; /* global */
/***********************************************************************
* CoGetState [OLE32.@]
*
* NOTES: might be incomplete
*/
static void COM_ExternalLockDelete(
COM_ExternalLock *itemList)
HRESULT WINAPI CoGetState(IUnknown ** ppv)
{
COM_ExternalLock *current = elList.head;
if ( current == itemList )
{
/*
* this section handles the deletion of the first node
*/
elList.head = itemList->next;
HeapFree( GetProcessHeap(), 0, itemList);
}
else
{
do
{
if ( current->next == itemList ) /* We found the item to free */
{
current->next = itemList->next; /* readjust the list pointers */
HeapFree( GetProcessHeap(), 0, itemList);
break;
}
FIXME("\n");
/* Skip to the next item */
current = current->next;
if(pUnkState) {
IUnknown_AddRef(pUnkState);
*ppv = pUnkState;
FIXME("-- %p\n", *ppv);
return S_OK;
}
*ppv = NULL;
return E_FAIL;
} while ( current != EL_END_OF_LIST );
}
}
/***********************************************************************
* DllEntryPoint [COMPOBJ.116]
*
* Initialization code for the COMPOBJ DLL
* CoSetState [OLE32.42]
*
* RETURNS:
* NOTES: FIXME: protect this with a crst
*/
BOOL WINAPI COMPOBJ_DllEntryPoint(DWORD Reason, HINSTANCE16 hInst, WORD ds, WORD HeapSize, DWORD res1, WORD res2)
HRESULT WINAPI CoSetState(IUnknown * pv)
{
TRACE("(%08lx, %04x, %04x, %04x, %08lx, %04x)\n", Reason, hInst, ds, HeapSize,
res1, res2);
switch(Reason)
{
case DLL_PROCESS_ATTACH:
if (!COMPOBJ_Attach++) COMPOBJ_hInstance = hInst;
break;
case DLL_PROCESS_DETACH:
if(!--COMPOBJ_Attach)
COMPOBJ_hInstance = 0;
break;
}
return TRUE;
FIXME("(%p),stub!\n", pv);
if (pv) {
IUnknown_AddRef(pv);
nStatCounter++;
if (nStatCounter == 1) LoadLibraryA("OLEAUT32.DLL");
}
if (pUnkState) {
TRACE("-- release %p now\n", pUnkState);
IUnknown_Release(pUnkState);
nStatCounter--;
if (!nStatCounter) FreeLibrary(hOleAut32);
}
pUnkState = pv;
return S_OK;
}
/******************************************************************************
* OleGetAutoConvert [OLE32.104]
*/
......@@ -2153,9 +1802,8 @@ HRESULT WINAPI OleGetAutoConvert(REFCLSID clsidOld, LPCLSID pClsidNew)
MultiByteToWideChar( CP_ACP, 0, buf, -1, wbuf, sizeof(wbuf)/sizeof(WCHAR) );
CLSIDFromString(wbuf,pClsidNew);
done:
if (hkey) RegCloseKey(hkey);
return res;
if (hkey) RegCloseKey(hkey);
return res;
}
/******************************************************************************
......
......@@ -116,4 +116,6 @@ HRESULT WINAPI RunningObjectTableImpl_UnInitialize();
/* This function decomposes a String path to a String Table containing all the elements ("\" or "subDirectory" or "Directory" or "FileName") of the path */
int WINAPI FileMonikerImpl_DecomposePath(LPCOLESTR str, LPOLESTR** stringTable);
HRESULT WINAPI __CLSIDFromStringA(LPCSTR idstr, CLSID *id);
#endif /* __WINE_OLE_COMPOBJ_H */
/*
* free threaded marshaler
*
* Copyright 2002 Juergen Schmied
*
* 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., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
*/
#include "config.h"
#include <stdlib.h>
#include <stdio.h>
#include <string.h>
#include <assert.h>
#include "winbase.h"
#include "wine/obj_base.h"
#include "wine/obj_storage.h"
#include "wine/obj_marshal.h"
#include "wine/debug.h"
WINE_DEFAULT_DEBUG_CHANNEL(ole);
typedef struct _FTMarshalImpl {
ICOM_VFIELD (IUnknown);
DWORD ref;
ICOM_VTABLE (IMarshal) * lpvtblFTM;
IUnknown *pUnkOuter;
} FTMarshalImpl;
#define _IFTMUnknown_(This)(IUnknown*)&(This->lpVtbl)
#define _IFTMarshal_(This) (IMarshal*)&(This->lpvtblFTM)
#define _IFTMarshall_Offset ((int)(&(((FTMarshalImpl*)0)->lpvtblFTM)))
#define _ICOM_THIS_From_IFTMarshal(class, name) class* This = (class*)(((char*)name)-_IFTMarshall_Offset);
/* inner IUnknown to handle aggregation */
HRESULT WINAPI IiFTMUnknown_fnQueryInterface (IUnknown * iface, REFIID riid, LPVOID * ppv)
{
ICOM_THIS (FTMarshalImpl, iface);
TRACE ("\n");
*ppv = NULL;
if (IsEqualIID (&IID_IUnknown, riid))
*ppv = _IFTMUnknown_ (This);
else if (IsEqualIID (&IID_IMarshal, riid))
*ppv = _IFTMarshal_ (This);
else {
FIXME ("No interface for %s.\n", debugstr_guid (riid));
return E_NOINTERFACE;
}
IUnknown_AddRef ((IUnknown *) * ppv);
return S_OK;
}
ULONG WINAPI IiFTMUnknown_fnAddRef (IUnknown * iface)
{
ICOM_THIS (FTMarshalImpl, iface);
TRACE ("\n");
return InterlockedIncrement (&This->ref);
}
ULONG WINAPI IiFTMUnknown_fnRelease (IUnknown * iface)
{
ICOM_THIS (FTMarshalImpl, iface);
TRACE ("\n");
if (InterlockedDecrement (&This->ref))
return This->ref;
HeapFree (GetProcessHeap (), 0, This);
return 0;
}
static ICOM_VTABLE (IUnknown) iunkvt =
{
ICOM_MSVTABLE_COMPAT_DummyRTTIVALUE
IiFTMUnknown_fnQueryInterface,
IiFTMUnknown_fnAddRef,
IiFTMUnknown_fnRelease
};
HRESULT WINAPI FTMarshalImpl_QueryInterface (LPMARSHAL iface, REFIID riid, LPVOID * ppv)
{
_ICOM_THIS_From_IFTMarshal (FTMarshalImpl, iface);
TRACE ("(%p)->(\n\tIID:\t%s,%p)\n", This, debugstr_guid (riid), ppv);
return IUnknown_QueryInterface (This->pUnkOuter, riid, ppv);
}
ULONG WINAPI FTMarshalImpl_AddRef (LPMARSHAL iface)
{
_ICOM_THIS_From_IFTMarshal (FTMarshalImpl, iface);
TRACE ("\n");
return IUnknown_AddRef (This->pUnkOuter);
}
ULONG WINAPI FTMarshalImpl_Release (LPMARSHAL iface)
{
_ICOM_THIS_From_IFTMarshal (FTMarshalImpl, iface);
TRACE ("\n");
return IUnknown_Release (This->pUnkOuter);
}
HRESULT WINAPI FTMarshalImpl_GetUnmarshalClass (LPMARSHAL iface, REFIID riid, void *pv, DWORD dwDestContext,
void *pvDestContext, DWORD mshlflags, CLSID * pCid)
{
FIXME ("(), stub!\n");
return S_OK;
}
HRESULT WINAPI FTMarshalImpl_GetMarshalSizeMax (LPMARSHAL iface, REFIID riid, void *pv, DWORD dwDestContext,
void *pvDestContext, DWORD mshlflags, DWORD * pSize)
{
IMarshal *pMarshal = NULL;
HRESULT hres;
_ICOM_THIS_From_IFTMarshal (FTMarshalImpl, iface);
FIXME ("(), stub!\n");
/* if the marshaling happends inside the same process the interface pointer is
copied between the appartments */
if (dwDestContext == MSHCTX_INPROC || dwDestContext == MSHCTX_CROSSCTX) {
*pSize = sizeof (This);
return S_OK;
}
/* use the standard marshaler to handle all other cases */
CoGetStandardMarshal (riid, pv, dwDestContext, pvDestContext, mshlflags, &pMarshal);
hres = IMarshal_GetMarshalSizeMax (pMarshal, riid, pv, dwDestContext, pvDestContext, mshlflags, pSize);
IMarshal_Release (pMarshal);
return hres;
return S_OK;
}
HRESULT WINAPI FTMarshalImpl_MarshalInterface (LPMARSHAL iface, IStream * pStm, REFIID riid, void *pv,
DWORD dwDestContext, void *pvDestContext, DWORD mshlflags)
{
IMarshal *pMarshal = NULL;
HRESULT hres;
_ICOM_THIS_From_IFTMarshal (FTMarshalImpl, iface);
FIXME ("(), stub!\n");
/* if the marshaling happends inside the same process the interface pointer is
copied between the appartments */
if (dwDestContext == MSHCTX_INPROC || dwDestContext == MSHCTX_CROSSCTX) {
return IStream_Write (pStm, This, sizeof (This), 0);
}
/* use the standard marshaler to handle all other cases */
CoGetStandardMarshal (riid, pv, dwDestContext, pvDestContext, mshlflags, &pMarshal);
hres = IMarshal_MarshalInterface (pMarshal, pStm, riid, pv, dwDestContext, pvDestContext, mshlflags);
IMarshal_Release (pMarshal);
return hres;
}
HRESULT WINAPI FTMarshalImpl_UnmarshalInterface (LPMARSHAL iface, IStream * pStm, REFIID riid, void **ppv)
{
FIXME ("(), stub!\n");
return S_OK;
}
HRESULT WINAPI FTMarshalImpl_ReleaseMarshalData (LPMARSHAL iface, IStream * pStm)
{
FIXME ("(), stub!\n");
return S_OK;
}
HRESULT WINAPI FTMarshalImpl_DisconnectObject (LPMARSHAL iface, DWORD dwReserved)
{
FIXME ("(), stub!\n");
return S_OK;
}
ICOM_VTABLE (IMarshal) ftmvtbl =
{
ICOM_MSVTABLE_COMPAT_DummyRTTIVALUE
FTMarshalImpl_QueryInterface,
FTMarshalImpl_AddRef,
FTMarshalImpl_Release,
FTMarshalImpl_GetUnmarshalClass,
FTMarshalImpl_GetMarshalSizeMax,
FTMarshalImpl_MarshalInterface,
FTMarshalImpl_UnmarshalInterface,
FTMarshalImpl_ReleaseMarshalData,
FTMarshalImpl_DisconnectObject
};
/***********************************************************************
* CoCreateFreeThreadedMarshaler [OLE32.5]
*
*/
HRESULT WINAPI CoCreateFreeThreadedMarshaler (LPUNKNOWN punkOuter, LPUNKNOWN * ppunkMarshal)
{
FTMarshalImpl *ftm;
TRACE ("(%p %p)\n", punkOuter, ppunkMarshal);
ftm = (FTMarshalImpl *) HeapAlloc (GetProcessHeap (), 0, sizeof (FTMarshalImpl));
if (!ftm)
return E_OUTOFMEMORY;
ICOM_VTBL (ftm) = &iunkvt;
ftm->lpvtblFTM = &ftmvtbl;
ftm->ref = 1;
ftm->pUnkOuter = punkOuter;
*ppunkMarshal = _IFTMUnknown_ (ftm);
return S_OK;
}
......@@ -27,156 +27,15 @@
#include "ole2.h"
#include "windef.h"
#include "winbase.h"
#include "winerror.h"
#include "wine/obj_base.h"
#include "wine/winbase16.h"
#include "ifs.h"
#include "wine/debug.h"
WINE_DEFAULT_DEBUG_CHANNEL(ole);
/* --- IMalloc16 implementation */
typedef struct
{
/* IUnknown fields */
ICOM_VFIELD(IMalloc16);
DWORD ref;
/* IMalloc16 fields */
} IMalloc16Impl;
/******************************************************************************
* IMalloc16_QueryInterface [COMPOBJ.500]
*/
HRESULT WINAPI IMalloc16_fnQueryInterface(IMalloc16* iface,REFIID refiid,LPVOID *obj) {
ICOM_THIS(IMalloc16Impl,iface);
TRACE("(%p)->QueryInterface(%s,%p)\n",This,debugstr_guid(refiid),obj);
if ( !memcmp(&IID_IUnknown,refiid,sizeof(IID_IUnknown)) ||
!memcmp(&IID_IMalloc,refiid,sizeof(IID_IMalloc))
) {
*obj = This;
return 0;
}
return OLE_E_ENUM_NOMORE;
}
/******************************************************************************
* IMalloc16_AddRef [COMPOBJ.501]
*/
ULONG WINAPI IMalloc16_fnAddRef(IMalloc16* iface) {
ICOM_THIS(IMalloc16Impl,iface);
TRACE("(%p)->AddRef()\n",This);
return 1; /* cannot be freed */
}
/******************************************************************************
* IMalloc16_Release [COMPOBJ.502]
*/
ULONG WINAPI IMalloc16_fnRelease(IMalloc16* iface) {
ICOM_THIS(IMalloc16Impl,iface);
TRACE("(%p)->Release()\n",This);
return 1; /* cannot be freed */
}
/******************************************************************************
* IMalloc16_Alloc [COMPOBJ.503]
*/
SEGPTR WINAPI IMalloc16_fnAlloc(IMalloc16* iface,DWORD cb) {
ICOM_THIS(IMalloc16Impl,iface);
TRACE("(%p)->Alloc(%ld)\n",This,cb);
return MapLS( HeapAlloc( GetProcessHeap(), 0, cb ) );
}
/******************************************************************************
* IMalloc16_Realloc [COMPOBJ.504]
*/
SEGPTR WINAPI IMalloc16_fnRealloc(IMalloc16* iface,SEGPTR pv,DWORD cb)
{
SEGPTR ret;
ICOM_THIS(IMalloc16Impl,iface);
TRACE("(%p)->Realloc(%08lx,%ld)\n",This,pv,cb);
ret = MapLS( HeapReAlloc( GetProcessHeap(), 0, MapSL(pv), cb ) );
UnMapLS(pv);
return ret;
}
/******************************************************************************
* IMalloc16_Free [COMPOBJ.505]
*/
VOID WINAPI IMalloc16_fnFree(IMalloc16* iface,SEGPTR pv)
{
void *ptr = MapSL(pv);
ICOM_THIS(IMalloc16Impl,iface);
TRACE("(%p)->Free(%08lx)\n",This,pv);
UnMapLS(pv);
HeapFree( GetProcessHeap(), 0, ptr );
}
/******************************************************************************
* IMalloc16_GetSize [COMPOBJ.506]
*/
DWORD WINAPI IMalloc16_fnGetSize(const IMalloc16* iface,SEGPTR pv)
{
ICOM_CTHIS(IMalloc16Impl,iface);
TRACE("(%p)->GetSize(%08lx)\n",This,pv);
return HeapSize( GetProcessHeap(), 0, MapSL(pv) );
}
/******************************************************************************
* IMalloc16_DidAlloc [COMPOBJ.507]
*/
INT16 WINAPI IMalloc16_fnDidAlloc(const IMalloc16* iface,LPVOID pv) {
ICOM_CTHIS(IMalloc16,iface);
TRACE("(%p)->DidAlloc(%p)\n",This,pv);
return (INT16)-1;
}
/******************************************************************************
* IMalloc16_HeapMinimize [COMPOBJ.508]
*/
LPVOID WINAPI IMalloc16_fnHeapMinimize(IMalloc16* iface) {
ICOM_THIS(IMalloc16Impl,iface);
TRACE("(%p)->HeapMinimize()\n",This);
return NULL;
}
/******************************************************************************
* IMalloc16_Constructor [VTABLE]
*/
LPMALLOC16
IMalloc16_Constructor()
{
static ICOM_VTABLE(IMalloc16) vt16;
static SEGPTR msegvt16;
IMalloc16Impl* This;
HMODULE16 hcomp = GetModuleHandle16("COMPOBJ");
This = HeapAlloc( GetProcessHeap(), 0, sizeof(IMalloc16Impl) );
if (!msegvt16)
{
#define VTENT(x) vt16.x = (void*)GetProcAddress16(hcomp,"IMalloc16_"#x);assert(vt16.x)
VTENT(QueryInterface);
VTENT(AddRef);
VTENT(Release);
VTENT(Alloc);
VTENT(Realloc);
VTENT(Free);
VTENT(GetSize);
VTENT(DidAlloc);
VTENT(HeapMinimize);
#undef VTENT
msegvt16 = MapLS( &vt16 );
}
ICOM_VTBL(This) = (ICOM_VTABLE(IMalloc16)*)msegvt16;
This->ref = 1;
return (LPMALLOC16)MapLS( This );
}
/******************************************************************************
* IMalloc32 implementation
*
......
/*
* 16 bit ole functions
*
* Copyright 1995 Martin von Loewis
* Copyright 1998 Justin Bradford
* Copyright 1999 Francis Beaudet
* Copyright 1999 Sylvain St-Germain
* Copyright 2002 Marcus Meissner
*
* 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., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
*/
#include "config.h"
#include <stdlib.h>
#include <stdio.h>
#include <string.h>
#include <assert.h>
#include "windef.h"
#include "objbase.h"
#include "ole2.h"
#include "ole2ver.h"
#include "rpc.h"
#include "winerror.h"
#include "winreg.h"
#include "wownt32.h"
#include "wtypes.h"
#include "wine/unicode.h"
#include "wine/obj_base.h"
#include "wine/obj_clientserver.h"
#include "wine/obj_misc.h"
#include "wine/obj_marshal.h"
#include "wine/obj_storage.h"
#include "wine/obj_channel.h"
#include "wine/winbase16.h"
#include "compobj_private.h"
#include "ifs.h"
#include "wine/winbase16.h"
#include "wine/debug.h"
WINE_DEFAULT_DEBUG_CHANNEL(ole);
HINSTANCE16 COMPOBJ_hInstance = 0;
static int COMPOBJ_Attach = 0;
HTASK16 hETask = 0;
WORD Table_ETask[62];
LPMALLOC16 currentMalloc16=NULL;
/* --- IMalloc16 implementation */
typedef struct
{
/* IUnknown fields */
ICOM_VFIELD(IMalloc16);
DWORD ref;
/* IMalloc16 fields */
} IMalloc16Impl;
/******************************************************************************
* IMalloc16_QueryInterface [COMPOBJ.500]
*/
HRESULT WINAPI IMalloc16_fnQueryInterface(IMalloc16* iface,REFIID refiid,LPVOID *obj) {
ICOM_THIS(IMalloc16Impl,iface);
TRACE("(%p)->QueryInterface(%s,%p)\n",This,debugstr_guid(refiid),obj);
if ( !memcmp(&IID_IUnknown,refiid,sizeof(IID_IUnknown)) ||
!memcmp(&IID_IMalloc,refiid,sizeof(IID_IMalloc))
) {
*obj = This;
return 0;
}
return OLE_E_ENUM_NOMORE;
}
/******************************************************************************
* IMalloc16_AddRef [COMPOBJ.501]
*/
ULONG WINAPI IMalloc16_fnAddRef(IMalloc16* iface) {
ICOM_THIS(IMalloc16Impl,iface);
TRACE("(%p)->AddRef()\n",This);
return 1; /* cannot be freed */
}
/******************************************************************************
* IMalloc16_Release [COMPOBJ.502]
*/
ULONG WINAPI IMalloc16_fnRelease(IMalloc16* iface) {
ICOM_THIS(IMalloc16Impl,iface);
TRACE("(%p)->Release()\n",This);
return 1; /* cannot be freed */
}
/******************************************************************************
* IMalloc16_Alloc [COMPOBJ.503]
*/
SEGPTR WINAPI IMalloc16_fnAlloc(IMalloc16* iface,DWORD cb) {
ICOM_THIS(IMalloc16Impl,iface);
TRACE("(%p)->Alloc(%ld)\n",This,cb);
return MapLS( HeapAlloc( GetProcessHeap(), 0, cb ) );
}
/******************************************************************************
* IMalloc16_Realloc [COMPOBJ.504]
*/
SEGPTR WINAPI IMalloc16_fnRealloc(IMalloc16* iface,SEGPTR pv,DWORD cb)
{
SEGPTR ret;
ICOM_THIS(IMalloc16Impl,iface);
TRACE("(%p)->Realloc(%08lx,%ld)\n",This,pv,cb);
ret = MapLS( HeapReAlloc( GetProcessHeap(), 0, MapSL(pv), cb ) );
UnMapLS(pv);
return ret;
}
/******************************************************************************
* IMalloc16_Free [COMPOBJ.505]
*/
VOID WINAPI IMalloc16_fnFree(IMalloc16* iface,SEGPTR pv)
{
void *ptr = MapSL(pv);
ICOM_THIS(IMalloc16Impl,iface);
TRACE("(%p)->Free(%08lx)\n",This,pv);
UnMapLS(pv);
HeapFree( GetProcessHeap(), 0, ptr );
}
/******************************************************************************
* IMalloc16_GetSize [COMPOBJ.506]
*/
DWORD WINAPI IMalloc16_fnGetSize(const IMalloc16* iface,SEGPTR pv)
{
ICOM_CTHIS(IMalloc16Impl,iface);
TRACE("(%p)->GetSize(%08lx)\n",This,pv);
return HeapSize( GetProcessHeap(), 0, MapSL(pv) );
}
/******************************************************************************
* IMalloc16_DidAlloc [COMPOBJ.507]
*/
INT16 WINAPI IMalloc16_fnDidAlloc(const IMalloc16* iface,LPVOID pv) {
ICOM_CTHIS(IMalloc16,iface);
TRACE("(%p)->DidAlloc(%p)\n",This,pv);
return (INT16)-1;
}
/******************************************************************************
* IMalloc16_HeapMinimize [COMPOBJ.508]
*/
LPVOID WINAPI IMalloc16_fnHeapMinimize(IMalloc16* iface) {
ICOM_THIS(IMalloc16Impl,iface);
TRACE("(%p)->HeapMinimize()\n",This);
return NULL;
}
/******************************************************************************
* IMalloc16_Constructor [VTABLE]
*/
LPMALLOC16
IMalloc16_Constructor()
{
static ICOM_VTABLE(IMalloc16) vt16;
static SEGPTR msegvt16;
IMalloc16Impl* This;
HMODULE16 hcomp = GetModuleHandle16("COMPOBJ");
This = HeapAlloc( GetProcessHeap(), 0, sizeof(IMalloc16Impl) );
if (!msegvt16)
{
#define VTENT(x) vt16.x = (void*)GetProcAddress16(hcomp,"IMalloc16_"#x);assert(vt16.x)
VTENT(QueryInterface);
VTENT(AddRef);
VTENT(Release);
VTENT(Alloc);
VTENT(Realloc);
VTENT(Free);
VTENT(GetSize);
VTENT(DidAlloc);
VTENT(HeapMinimize);
#undef VTENT
msegvt16 = MapLS( &vt16 );
}
ICOM_VTBL(This) = (ICOM_VTABLE(IMalloc16)*)msegvt16;
This->ref = 1;
return (LPMALLOC16)MapLS( This );
}
/***********************************************************************
* CoGetMalloc [COMPOBJ.4]
* RETURNS
* The current win16 IMalloc
*/
HRESULT WINAPI CoGetMalloc16(
DWORD dwMemContext, /* [in] unknown */
LPMALLOC16 * lpMalloc /* [out] current win16 malloc interface */
) {
if(!currentMalloc16)
currentMalloc16 = IMalloc16_Constructor();
*lpMalloc = currentMalloc16;
return S_OK;
}
/***********************************************************************
* CoCreateStandardMalloc [COMPOBJ.71]
*/
HRESULT WINAPI CoCreateStandardMalloc16(DWORD dwMemContext,
LPMALLOC16 *lpMalloc)
{
/* FIXME: docu says we shouldn't return the same allocator as in
* CoGetMalloc16 */
*lpMalloc = IMalloc16_Constructor();
return S_OK;
}
/******************************************************************************
* CoInitialize [COMPOBJ.2]
* Set the win16 IMalloc used for memory management
*/
HRESULT WINAPI CoInitialize16(
LPVOID lpReserved /* [in] pointer to win16 malloc interface */
) {
currentMalloc16 = (LPMALLOC16)lpReserved;
return S_OK;
}
/***********************************************************************
* CoUninitialize [COMPOBJ.3]
* Don't know what it does.
* 3-Nov-98 -- this was originally misspelled, I changed it to what I
* believe is the correct spelling
*/
void WINAPI CoUninitialize16(void)
{
TRACE("()\n");
CoFreeAllLibraries();
}
/***********************************************************************
* IsEqualGUID [COMPOBJ.18]
*
* Compares two Unique Identifiers.
*
* RETURNS
* TRUE if equal
*/
BOOL16 WINAPI IsEqualGUID16(
GUID* g1, /* [in] unique id 1 */
GUID* g2) /* [in] unique id 2 */
{
return !memcmp( g1, g2, sizeof(GUID) );
}
/******************************************************************************
* CLSIDFromString [COMPOBJ.20]
* Converts a unique identifier from its string representation into
* the GUID struct.
*
* Class id: DWORD-WORD-WORD-BYTES[2]-BYTES[6]
*
* RETURNS
* the converted GUID
*/
HRESULT WINAPI CLSIDFromString16(
LPCOLESTR16 idstr, /* [in] string representation of guid */
CLSID *id) /* [out] GUID converted from string */
{
return __CLSIDFromStringA(idstr,id);
}
extern BOOL WINAPI K32WOWCallback16Ex( DWORD vpfn16, DWORD dwFlags,
DWORD cbArgs, LPVOID pArgs,
LPDWORD pdwRetCode );
/******************************************************************************
* _xmalloc16 [internal]
* Allocates size bytes from the standard ole16 allocator.
*
* RETURNS
* the allocated segmented pointer and a HRESULT
*/
HRESULT
_xmalloc16(DWORD size, SEGPTR *ptr) {
LPMALLOC16 mllc;
DWORD args[2];
if (CoGetMalloc16(0,&mllc))
return E_OUTOFMEMORY;
args[0] = (DWORD)mllc;
args[1] = size;
/* No need for a Callback entry, we have WOWCallback16Ex which does
* everything we need.
*/
if (!K32WOWCallback16Ex(
(DWORD)((ICOM_VTABLE(IMalloc16)*)MapSL(
(SEGPTR)ICOM_VTBL(((LPMALLOC16)MapSL((SEGPTR)mllc))))
)->Alloc,
WCB16_CDECL,
2*sizeof(DWORD),
(LPVOID)args,
(LPDWORD)ptr
)) {
ERR("CallTo16 IMalloc16 (%ld) failed\n",size);
return E_FAIL;
}
return S_OK;
}
/******************************************************************************
* StringFromCLSID [COMPOBJ.19]
* Converts a GUID into the respective string representation.
* The target string is allocated using the OLE IMalloc.
*
* RETURNS
* the string representation and HRESULT
*/
HRESULT WINAPI StringFromCLSID16(
REFCLSID id, /* [in] the GUID to be converted */
LPOLESTR16 *idstr /* [out] a pointer to a to-be-allocated segmented pointer pointing to the resulting string */
) {
HRESULT ret;
ret = _xmalloc16(40,(SEGPTR*)idstr);
if (ret != S_OK)
return ret;
return WINE_StringFromCLSID(id,MapSL((SEGPTR)*idstr));
}
/******************************************************************************
* ProgIDFromCLSID [COMPOBJ.62]
* Converts a class id into the respective Program ID. (By using a registry lookup)
* RETURNS S_OK on success
* riid associated with the progid
*/
HRESULT WINAPI ProgIDFromCLSID16(
REFCLSID clsid, /* [in] class id as found in registry */
LPOLESTR16 *lplpszProgID/* [out] associated Prog ID */
) {
char strCLSID[50], *buf, *buf2;
DWORD buf2len;
HKEY xhkey;
HRESULT ret = S_OK;
WINE_StringFromCLSID(clsid, strCLSID);
buf = HeapAlloc(GetProcessHeap(), 0, strlen(strCLSID)+14);
sprintf(buf,"CLSID\\%s\\ProgID", strCLSID);
if (RegOpenKeyA(HKEY_CLASSES_ROOT, buf, &xhkey))
ret = REGDB_E_CLASSNOTREG;
HeapFree(GetProcessHeap(), 0, buf);
if (ret == S_OK)
{
buf2 = HeapAlloc(GetProcessHeap(), 0, 255);
buf2len = 255;
if (RegQueryValueA(xhkey, NULL, buf2, &buf2len))
ret = REGDB_E_CLASSNOTREG;
if (ret == S_OK)
{
ret = _xmalloc16(buf2len+1, (SEGPTR*)lplpszProgID);
if (ret != S_OK)
return ret;
strcpy(MapSL((SEGPTR)*lplpszProgID),buf2);
ret = S_OK;
}
HeapFree(GetProcessHeap(), 0, buf2);
}
RegCloseKey(xhkey);
return ret;
}
/******************************************************************************
* CLSIDFromProgID [COMPOBJ.61]
* Converts a program id into the respective GUID. (By using a registry lookup)
* RETURNS
* riid associated with the progid
*/
HRESULT WINAPI CLSIDFromProgID16(
LPCOLESTR16 progid, /* [in] program id as found in registry */
LPCLSID riid /* [out] associated CLSID */
) {
char *buf,buf2[80];
DWORD buf2len;
HRESULT err;
HKEY xhkey;
buf = HeapAlloc(GetProcessHeap(),0,strlen(progid)+8);
sprintf(buf,"%s\\CLSID",progid);
if ((err=RegOpenKeyA(HKEY_CLASSES_ROOT,buf,&xhkey))) {
HeapFree(GetProcessHeap(),0,buf);
return CO_E_CLASSSTRING;
}
HeapFree(GetProcessHeap(),0,buf);
buf2len = sizeof(buf2);
if ((err=RegQueryValueA(xhkey,NULL,buf2,&buf2len))) {
RegCloseKey(xhkey);
return CO_E_CLASSSTRING;
}
RegCloseKey(xhkey);
return __CLSIDFromStringA(buf2,riid);
}
/***********************************************************************
* LookupETask (COMPOBJ.94)
*/
HRESULT WINAPI LookupETask16(HTASK16 *hTask,LPVOID p) {
FIXME("(%p,%p),stub!\n",hTask,p);
if ((*hTask = GetCurrentTask()) == hETask) {
memcpy(p, Table_ETask, sizeof(Table_ETask));
}
return 0;
}
/***********************************************************************
* SetETask (COMPOBJ.95)
*/
HRESULT WINAPI SetETask16(HTASK16 hTask, LPVOID p) {
FIXME("(%04x,%p),stub!\n",hTask,p);
hETask = hTask;
return 0;
}
/***********************************************************************
* CALLOBJECTINWOW (COMPOBJ.201)
*/
HRESULT WINAPI CallObjectInWOW(LPVOID p1,LPVOID p2) {
FIXME("(%p,%p),stub!\n",p1,p2);
return 0;
}
/******************************************************************************
* CoRegisterClassObject [COMPOBJ.5]
*
* Don't know where it registers it ...
*/
HRESULT WINAPI CoRegisterClassObject16(
REFCLSID rclsid,
LPUNKNOWN pUnk,
DWORD dwClsContext, /* [in] CLSCTX flags indicating the context in which to run the executable */
DWORD flags, /* [in] REGCLS flags indicating how connections are made */
LPDWORD lpdwRegister
) {
char buf[80];
WINE_StringFromCLSID(rclsid,buf);
FIXME("(%s,%p,0x%08lx,0x%08lx,%p),stub\n",
buf,pUnk,dwClsContext,flags,lpdwRegister
);
return 0;
}
/******************************************************************************
* CoRevokeClassObject [COMPOBJ.6]
*
*/
HRESULT WINAPI CoRevokeClassObject16(DWORD dwRegister) /* [in] token on class obj */
{
FIXME("(0x%08lx),stub!\n", dwRegister);
return 0;
}
/******************************************************************************
* CoFileTimeToDosDateTime [COMPOBJ.30]
*/
BOOL16 WINAPI CoFileTimeToDosDateTime16(const FILETIME *ft, LPWORD lpDosDate, LPWORD lpDosTime)
{
return FileTimeToDosDateTime(ft, lpDosDate, lpDosTime);
}
/******************************************************************************
* CoDosDateTimeToFileTime [COMPOBJ.31]
*/
BOOL16 WINAPI CoDosDateTimeToFileTime16(WORD wDosDate, WORD wDosTime, FILETIME *ft)
{
return DosDateTimeToFileTime(wDosDate, wDosTime, ft);
}
/******************************************************************************
* CoRegisterMessageFilter [COMPOBJ.27]
*/
HRESULT WINAPI CoRegisterMessageFilter16(
LPMESSAGEFILTER lpMessageFilter,
LPMESSAGEFILTER *lplpMessageFilter
) {
FIXME("(%p,%p),stub!\n",lpMessageFilter,lplpMessageFilter);
return 0;
}
/******************************************************************************
* CoLockObjectExternal [COMPOBJ.63]
*/
HRESULT WINAPI CoLockObjectExternal16(
LPUNKNOWN pUnk, /* [in] object to be locked */
BOOL16 fLock, /* [in] do lock */
BOOL16 fLastUnlockReleases /* [in] ? */
) {
FIXME("(%p,%d,%d),stub!\n",pUnk,fLock,fLastUnlockReleases);
return S_OK;
}
/***********************************************************************
* CoGetState [COMPOBJ.115]
*/
HRESULT WINAPI CoGetState16(LPDWORD state)
{
FIXME("(%p),stub!\n", state);
*state = 0;
return S_OK;
}
/***********************************************************************
* DllEntryPoint [COMPOBJ.116]
*
* Initialization code for the COMPOBJ DLL
*
* RETURNS:
*/
BOOL WINAPI COMPOBJ_DllEntryPoint(DWORD Reason, HINSTANCE16 hInst, WORD ds, WORD HeapSize, DWORD res1, WORD res2)
{
TRACE("(%08lx, %04x, %04x, %04x, %08lx, %04x)\n", Reason, hInst, ds, HeapSize, res1, res2);
switch(Reason)
{
case DLL_PROCESS_ATTACH:
if (!COMPOBJ_Attach++) COMPOBJ_hInstance = hInst;
break;
case DLL_PROCESS_DETACH:
if(!--COMPOBJ_Attach)
COMPOBJ_hInstance = 0;
break;
}
return TRUE;
}
......@@ -123,7 +123,14 @@ typedef enum tagCLSCTX
CLSCTX_INPROC_HANDLER16 = 0x20,
CLSCTX_INPROC_SERVERX86 = 0x40,
CLSCTX_INPROC_HANDLERX86 = 0x80,
CLSCTX_ESERVER_HANDLER = 0x100
CLSCTX_ESERVER_HANDLER = 0x100,
CLSCTX_NO_CODE_DOWNLOAD = 0x400,
CLSCTX_NO_CUSTOM_MARSHAL = 0x1000,
CLSCTX_ENABLE_CODE_DOWNLOAD = 0x2000,
CLSCTX_NO_FAILURE_LOG = 0x4000,
CLSCTX_DISABLE_AAA = 0x8000,
CLSCTX_ENABLE_AAA = 0x10000,
CLSCTX_FROM_DEFAULT_CONTEXT = 0x20000
} CLSCTX;
#define CLSCTX_INPROC (CLSCTX_INPROC_SERVER | CLSCTX_INPROC_HANDLER)
......@@ -143,7 +150,8 @@ typedef enum tagMSHCTX
MSHCTX_LOCAL = 0,
MSHCTX_NOSHAREDMEM = 1,
MSHCTX_DIFFERENTMACHINE = 2,
MSHCTX_INPROC = 3
MSHCTX_INPROC = 3,
MSHCTX_CROSSCTX = 4
} MSHCTX;
typedef unsigned short VARTYPE;
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment