wine-wine/dlls/comcat/register.c

343 lines
10 KiB
C

/*
* ComCatMgr ICatRegister implementation for comcat.dll
*
* Copyright (C) 2002 John K. Hohm
*
* 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
*/
#include "comcat_private.h"
#include "wine/debug.h"
WINE_DEFAULT_DEBUG_CHANNEL(ole);
/**********************************************************************
* File-scope string constants
*/
static const WCHAR comcat_keyname[21] = {
'C', 'o', 'm', 'p', 'o', 'n', 'e', 'n', 't', ' ', 'C', 'a',
't', 'e', 'g', 'o', 'r', 'i', 'e', 's', 0 };
static const WCHAR impl_keyname[23] = {
'I', 'm', 'p', 'l', 'e', 'm', 'e', 'n',
't', 'e', 'd', ' ', 'C', 'a', 't', 'e',
'g', 'o', 'r', 'i', 'e', 's', 0 };
static const WCHAR req_keyname[20] = {
'R', 'e', 'q', 'u', 'i', 'r', 'e', 'd',
' ', 'C', 'a', 't', 'e', 'g', 'o', 'r',
'i', 'e', 's', 0 };
static HRESULT COMCAT_RegisterClassCategories(
REFCLSID rclsid, LPCWSTR type,
ULONG cCategories, CATID *rgcatid);
static HRESULT COMCAT_UnRegisterClassCategories(
REFCLSID rclsid, LPCWSTR type,
ULONG cCategories, CATID *rgcatid);
/**********************************************************************
* COMCAT_ICatRegister_QueryInterface
*/
static HRESULT WINAPI COMCAT_ICatRegister_QueryInterface(
LPCATREGISTER iface,
REFIID riid,
LPVOID *ppvObj)
{
ICOM_THIS_MULTI(ComCatMgrImpl, regVtbl, iface);
TRACE("\n\tIID:\t%s\n",debugstr_guid(riid));
if (This == NULL || ppvObj == NULL) return E_POINTER;
return IUnknown_QueryInterface((LPUNKNOWN)&This->unkVtbl, riid, ppvObj);
}
/**********************************************************************
* COMCAT_ICatRegister_AddRef
*/
static ULONG WINAPI COMCAT_ICatRegister_AddRef(LPCATREGISTER iface)
{
ICOM_THIS_MULTI(ComCatMgrImpl, regVtbl, iface);
TRACE("\n");
if (This == NULL) return E_POINTER;
return IUnknown_AddRef((LPUNKNOWN)&This->unkVtbl);
}
/**********************************************************************
* COMCAT_ICatRegister_Release
*/
static ULONG WINAPI COMCAT_ICatRegister_Release(LPCATREGISTER iface)
{
ICOM_THIS_MULTI(ComCatMgrImpl, regVtbl, iface);
TRACE("\n");
if (This == NULL) return E_POINTER;
return IUnknown_Release((LPUNKNOWN)&This->unkVtbl);
}
/**********************************************************************
* COMCAT_ICatRegister_RegisterCategories
*/
static HRESULT WINAPI COMCAT_ICatRegister_RegisterCategories(
LPCATREGISTER iface,
ULONG cCategories,
CATEGORYINFO *rgci)
{
/* ICOM_THIS_MULTI(ComCatMgrImpl, regVtbl, iface); */
HKEY comcat_key;
HRESULT res;
TRACE("\n");
if (iface == NULL || (cCategories && rgci == NULL))
return E_POINTER;
/* Create (or open) the component categories key. */
res = RegCreateKeyExW(HKEY_CLASSES_ROOT, comcat_keyname, 0, NULL, 0,
KEY_READ | KEY_WRITE, NULL, &comcat_key, NULL);
if (res != ERROR_SUCCESS) return E_FAIL;
for (; cCategories; --cCategories, ++rgci) {
WCHAR fmt[4] = { '%', 'l', 'X', 0 };
WCHAR keyname[39];
WCHAR valname[9];
HKEY cat_key;
/* Create (or open) the key for this category. */
if (!StringFromGUID2(&rgci->catid, keyname, 39)) continue;
res = RegCreateKeyExW(comcat_key, keyname, 0, NULL, 0,
KEY_READ | KEY_WRITE, NULL, &cat_key, NULL);
if (res != ERROR_SUCCESS) continue;
/* Set the value for this locale's description. */
wsprintfW(valname, fmt, rgci->lcid);
RegSetValueExW(cat_key, valname, 0, REG_SZ,
(CONST BYTE*)(rgci->szDescription),
(lstrlenW(rgci->szDescription) + 1) * sizeof(WCHAR));
RegCloseKey(cat_key);
}
RegCloseKey(comcat_key);
return S_OK;
}
/**********************************************************************
* COMCAT_ICatRegister_UnRegisterCategories
*/
static HRESULT WINAPI COMCAT_ICatRegister_UnRegisterCategories(
LPCATREGISTER iface,
ULONG cCategories,
CATID *rgcatid)
{
/* ICOM_THIS_MULTI(ComCatMgrImpl, regVtbl, iface); */
HKEY comcat_key;
HRESULT res;
TRACE("\n");
if (iface == NULL || (cCategories && rgcatid == NULL))
return E_POINTER;
/* Open the component categories key. */
res = RegOpenKeyExW(HKEY_CLASSES_ROOT, comcat_keyname, 0,
KEY_READ | KEY_WRITE, &comcat_key);
if (res != ERROR_SUCCESS) return E_FAIL;
for (; cCategories; --cCategories, ++rgcatid) {
WCHAR keyname[39];
/* Delete the key for this category. */
if (!StringFromGUID2(rgcatid, keyname, 39)) continue;
RegDeleteKeyW(comcat_key, keyname);
}
RegCloseKey(comcat_key);
return S_OK;
}
/**********************************************************************
* COMCAT_ICatRegister_RegisterClassImplCategories
*/
static HRESULT WINAPI COMCAT_ICatRegister_RegisterClassImplCategories(
LPCATREGISTER iface,
REFCLSID rclsid,
ULONG cCategories,
CATID *rgcatid)
{
/* ICOM_THIS_MULTI(ComCatMgrImpl, regVtbl, iface); */
TRACE("\n");
return COMCAT_RegisterClassCategories(
rclsid, impl_keyname, cCategories, rgcatid);
}
/**********************************************************************
* COMCAT_ICatRegister_UnRegisterClassImplCategories
*/
static HRESULT WINAPI COMCAT_ICatRegister_UnRegisterClassImplCategories(
LPCATREGISTER iface,
REFCLSID rclsid,
ULONG cCategories,
CATID *rgcatid)
{
/* ICOM_THIS_MULTI(ComCatMgrImpl, regVtbl, iface); */
TRACE("\n");
return COMCAT_UnRegisterClassCategories(
rclsid, impl_keyname, cCategories, rgcatid);
}
/**********************************************************************
* COMCAT_ICatRegister_RegisterClassReqCategories
*/
static HRESULT WINAPI COMCAT_ICatRegister_RegisterClassReqCategories(
LPCATREGISTER iface,
REFCLSID rclsid,
ULONG cCategories,
CATID *rgcatid)
{
/* ICOM_THIS_MULTI(ComCatMgrImpl, regVtbl, iface); */
TRACE("\n");
return COMCAT_RegisterClassCategories(
rclsid, req_keyname, cCategories, rgcatid);
}
/**********************************************************************
* COMCAT_ICatRegister_UnRegisterClassReqCategories
*/
static HRESULT WINAPI COMCAT_ICatRegister_UnRegisterClassReqCategories(
LPCATREGISTER iface,
REFCLSID rclsid,
ULONG cCategories,
CATID *rgcatid)
{
/* ICOM_THIS_MULTI(ComCatMgrImpl, regVtbl, iface); */
TRACE("\n");
return COMCAT_UnRegisterClassCategories(
rclsid, req_keyname, cCategories, rgcatid);
}
/**********************************************************************
* COMCAT_ICatRegister_Vtbl
*/
const ICatRegisterVtbl COMCAT_ICatRegister_Vtbl =
{
COMCAT_ICatRegister_QueryInterface,
COMCAT_ICatRegister_AddRef,
COMCAT_ICatRegister_Release,
COMCAT_ICatRegister_RegisterCategories,
COMCAT_ICatRegister_UnRegisterCategories,
COMCAT_ICatRegister_RegisterClassImplCategories,
COMCAT_ICatRegister_UnRegisterClassImplCategories,
COMCAT_ICatRegister_RegisterClassReqCategories,
COMCAT_ICatRegister_UnRegisterClassReqCategories
};
/**********************************************************************
* COMCAT_RegisterClassCategories
*/
static HRESULT COMCAT_RegisterClassCategories(
REFCLSID rclsid,
LPCWSTR type,
ULONG cCategories,
CATID *rgcatid)
{
WCHAR keyname[39];
HRESULT res;
HKEY clsid_key, class_key, type_key;
if (cCategories && rgcatid == NULL) return E_POINTER;
/* Format the class key name. */
res = StringFromGUID2(rclsid, keyname, 39);
if (FAILED(res)) return res;
/* Create (or open) the CLSID key. */
res = RegCreateKeyExW(HKEY_CLASSES_ROOT, clsid_keyname, 0, NULL, 0,
KEY_READ | KEY_WRITE, NULL, &clsid_key, NULL);
if (res != ERROR_SUCCESS) return E_FAIL;
/* Create (or open) the class key. */
res = RegCreateKeyExW(clsid_key, keyname, 0, NULL, 0,
KEY_READ | KEY_WRITE, NULL, &class_key, NULL);
if (res == ERROR_SUCCESS) {
/* Create (or open) the category type key. */
res = RegCreateKeyExW(class_key, type, 0, NULL, 0,
KEY_READ | KEY_WRITE, NULL, &type_key, NULL);
if (res == ERROR_SUCCESS) {
for (; cCategories; --cCategories, ++rgcatid) {
HKEY key;
/* Format the category key name. */
res = StringFromGUID2(rgcatid, keyname, 39);
if (FAILED(res)) continue;
/* Do the register. */
res = RegCreateKeyExW(type_key, keyname, 0, NULL, 0,
KEY_READ | KEY_WRITE, NULL, &key, NULL);
if (res == ERROR_SUCCESS) RegCloseKey(key);
}
res = S_OK;
} else res = E_FAIL;
RegCloseKey(class_key);
} else res = E_FAIL;
RegCloseKey(clsid_key);
return res;
}
/**********************************************************************
* COMCAT_UnRegisterClassCategories
*/
static HRESULT COMCAT_UnRegisterClassCategories(
REFCLSID rclsid,
LPCWSTR type,
ULONG cCategories,
CATID *rgcatid)
{
WCHAR keyname[68] = { 'C', 'L', 'S', 'I', 'D', '\\' };
HRESULT res;
HKEY type_key;
if (cCategories && rgcatid == NULL) return E_POINTER;
/* Format the class category type key name. */
res = StringFromGUID2(rclsid, keyname + 6, 39);
if (FAILED(res)) return res;
keyname[44] = '\\';
lstrcpyW(keyname + 45, type);
/* Open the class category type key. */
res = RegOpenKeyExW(HKEY_CLASSES_ROOT, keyname, 0,
KEY_READ | KEY_WRITE, &type_key);
if (res != ERROR_SUCCESS) return E_FAIL;
for (; cCategories; --cCategories, ++rgcatid) {
/* Format the category key name. */
res = StringFromGUID2(rgcatid, keyname, 39);
if (FAILED(res)) continue;
/* Do the unregister. */
RegDeleteKeyW(type_key, keyname);
}
RegCloseKey(type_key);
return S_OK;
}