Leaked source code of windows server 2003
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
 
 
 
 
 
 

290 lines
8.2 KiB

//
// regsvr.cpp
//
#include "private.h"
#include "regsvr.h"
#include "cregkey.h"
#include <advpub.h>
//+------------------------------------------------------------------------
//
// Function: CLSIDToString
//
// Synopsis: Converts a CLSID to an mbcs string.
//
//-------------------------------------------------------------------------
static const BYTE GuidMap[] = {3, 2, 1, 0, '-', 5, 4, '-', 7, 6, '-',
8, 9, '-', 10, 11, 12, 13, 14, 15};
static const char szDigits[] = "0123456789ABCDEF";
BOOL CLSIDToStringA(REFGUID refGUID, char *pchA)
{
int i;
char *p = pchA;
const BYTE * pBytes = (const BYTE *) &refGUID;
*p++ = '{';
for (i = 0; i < sizeof(GuidMap); i++)
{
if (GuidMap[i] == '-')
{
*p++ = '-';
}
else
{
*p++ = szDigits[ (pBytes[GuidMap[i]] & 0xF0) >> 4 ];
*p++ = szDigits[ (pBytes[GuidMap[i]] & 0x0F) ];
}
}
*p++ = '}';
*p = '\0';
return TRUE;
}
//+------------------------------------------------------------------------
//
// Function: StringToCLSID
//
// Synopsis: Converts a CLSID to an mbcs string.
//
//-------------------------------------------------------------------------
BOOL HexStringToDword(LPCSTR &lpsz, DWORD &Value, int cDigits, WCHAR chDelim)
{
int Count;
Value = 0;
for (Count = 0; Count < cDigits; Count++, lpsz++)
{
if (*lpsz >= '0' && *lpsz <= '9')
Value = (Value << 4) + *lpsz - '0';
else if (*lpsz >= 'A' && *lpsz <= 'F')
Value = (Value << 4) + *lpsz - 'A' + 10;
else if (*lpsz >= 'a' && *lpsz <= 'f')
Value = (Value << 4) + *lpsz - 'a' + 10;
else
return(FALSE);
}
if (chDelim != 0)
return *lpsz++ == chDelim;
else
return TRUE;
}
BOOL StringAToCLSID(char *pchA, GUID *pGUID)
{
DWORD dw;
char *lpsz;
if (*pchA != '{')
return FALSE;
lpsz = ++pchA;
if (!HexStringToDword(lpsz, pGUID->Data1, sizeof(DWORD)*2, '-'))
return FALSE;
if (!HexStringToDword(lpsz, dw, sizeof(WORD)*2, '-'))
return FALSE;
pGUID->Data2 = (WORD)dw;
if (!HexStringToDword(lpsz, dw, sizeof(WORD)*2, '-'))
return FALSE;
pGUID->Data3 = (WORD)dw;
if (!HexStringToDword(lpsz, dw, sizeof(BYTE)*2, 0))
return FALSE;
pGUID->Data4[0] = (BYTE)dw;
if (!HexStringToDword(lpsz, dw, sizeof(BYTE)*2, '-'))
return FALSE;
pGUID->Data4[1] = (BYTE)dw;
if (!HexStringToDword(lpsz, dw, sizeof(BYTE)*2, 0))
return FALSE;
pGUID->Data4[2] = (BYTE)dw;
if (!HexStringToDword(lpsz, dw, sizeof(BYTE)*2, 0))
return FALSE;
pGUID->Data4[3] = (BYTE)dw;
if (!HexStringToDword(lpsz, dw, sizeof(BYTE)*2, 0))
return FALSE;
pGUID->Data4[4] = (BYTE)dw;
if (!HexStringToDword(lpsz, dw, sizeof(BYTE)*2, 0))
return FALSE;
pGUID->Data4[5] = (BYTE)dw;
if (!HexStringToDword(lpsz, dw, sizeof(BYTE)*2, 0))
return FALSE;
pGUID->Data4[6] = (BYTE)dw;
if (!HexStringToDword(lpsz, dw, sizeof(BYTE)*2, '}'))
return FALSE;
pGUID->Data4[7] = (BYTE)dw;
return (*lpsz == '\0');
}
//+------------------------------------------------------------------------
//
// Function: CLSIDToString
//
// Synopsis: Converts a CLSID to an mbcs string.
//
//-------------------------------------------------------------------------
static const WCHAR wszDigits[] = L"0123456789ABCDEF";
BOOL CLSIDToStringW(REFGUID refGUID, WCHAR *pchW)
{
int i;
WCHAR *p = pchW;
const BYTE * pBytes = (const BYTE *) &refGUID;
*p++ = L'{';
for (i = 0; i < sizeof(GuidMap); i++)
{
if (GuidMap[i] == '-')
{
*p++ = L'-';
}
else
{
*p++ = wszDigits[ (pBytes[GuidMap[i]] & 0xF0) >> 4 ];
*p++ = wszDigits[ (pBytes[GuidMap[i]] & 0x0F) ];
}
}
*p++ = L'}';
*p = L'\0';
return TRUE;
}
//RecurseDeleteKey is necessary because on NT RegDeleteKey doesn't work if the
//specified key has subkeys
LONG RecurseDeleteKey(HKEY hParentKey, LPCTSTR lpszKey)
{
HKEY hKey;
LONG lRes;
FILETIME time;
TCHAR szBuffer[256];
DWORD dwSize = sizeof(szBuffer);
if (RegOpenKey(hParentKey, lpszKey, &hKey) != ERROR_SUCCESS)
return ERROR_SUCCESS; // let's assume we couldn't open it because it's not there
lRes = ERROR_SUCCESS;
while (RegEnumKeyEx(hKey, 0, szBuffer, &dwSize, NULL, NULL, NULL, &time)==ERROR_SUCCESS)
{
lRes = RecurseDeleteKey(hKey, szBuffer);
if (lRes != ERROR_SUCCESS)
break;
dwSize = sizeof(szBuffer);
}
RegCloseKey(hKey);
return lRes == ERROR_SUCCESS ? RegDeleteKey(hParentKey, lpszKey) : lRes;
}
// set pszDesc == NULL to unregister, otherwise register
BOOL RegisterServer(REFCLSID clsid, LPCTSTR pszDesc, LPCTSTR pszPath, LPCTSTR pszModel, LPCTSTR pszSoftwareKey)
{
static const TCHAR c_szInfoKeyPrefix[] = TEXT("CLSID\\");
static const TCHAR c_szInProcSvr32[] = TEXT("InProcServer32");
static const TCHAR c_szModelName[] = TEXT("ThreadingModel");
TCHAR achIMEKey[ARRAYSIZE(c_szInfoKeyPrefix) + CLSID_STRLEN];
DWORD dw;
HKEY hKey;
HKEY hSubKey;
BOOL fRet;
if (!CLSIDToStringA(clsid, achIMEKey + ARRAYSIZE(c_szInfoKeyPrefix) - 1))
return FALSE;
memcpy(achIMEKey, c_szInfoKeyPrefix, sizeof(c_szInfoKeyPrefix)-sizeof(TCHAR));
if (pszDesc != NULL)
{
if (fRet = RegCreateKeyEx(HKEY_CLASSES_ROOT, achIMEKey, 0, NULL, REG_OPTION_NON_VOLATILE, KEY_WRITE, NULL, &hKey, &dw)
== ERROR_SUCCESS)
{
fRet &= RegSetValueEx(hKey, NULL, 0, REG_SZ, (BYTE *)pszDesc, (lstrlen(pszDesc)+1)*sizeof(TCHAR))
== ERROR_SUCCESS;
if (fRet &= RegCreateKeyEx(hKey, c_szInProcSvr32, 0, NULL, REG_OPTION_NON_VOLATILE, KEY_WRITE, NULL, &hSubKey, &dw)
== ERROR_SUCCESS)
{
fRet &= RegSetValueEx(hSubKey, NULL, 0, REG_SZ, (BYTE *)pszPath, (lstrlen(pszPath)+1)*sizeof(TCHAR)) == ERROR_SUCCESS;
fRet &= RegSetValueEx(hSubKey, c_szModelName, 0, REG_SZ, (BYTE *)pszModel, (lstrlen(pszModel)+1)*sizeof(TCHAR)) == ERROR_SUCCESS;
RegCloseKey(hSubKey);
}
RegCloseKey(hKey);
}
}
else
{
fRet = (RecurseDeleteKey(HKEY_CLASSES_ROOT, achIMEKey) == ERROR_SUCCESS) &&
(pszSoftwareKey == NULL || RecurseDeleteKey(HKEY_LOCAL_MACHINE, pszSoftwareKey) == ERROR_SUCCESS);
}
return fRet;
}
// set pszDesc == NULL to unregister, otherwise register
BOOL RegisterServerW(REFCLSID clsid, const WCHAR *pszDesc, const WCHAR *pszPath, const WCHAR *pszModel, const WCHAR *pszSoftwareKey, const WCHAR *pszMenuTextPUI)
{
static const WCHAR c_wszInfoKeyPrefix[] = L"CLSID\\";
static const WCHAR c_wszInProcSvr32[] = L"InProcServer32";
static const WCHAR c_wszModelName[] = L"ThreadingModel";
static const WCHAR c_wszMenuTextPUI[] = L"MenuTextPUI";
WCHAR achIMEKey[ARRAYSIZE(c_wszInfoKeyPrefix) + CLSID_STRLEN];
CMyRegKey hKey;
CMyRegKey hSubKey;
BOOL fRet = FALSE;
if (!CLSIDToStringW(clsid, achIMEKey + ARRAYSIZE(c_wszInfoKeyPrefix) - 1))
return fRet;
memcpy(achIMEKey, c_wszInfoKeyPrefix, sizeof(c_wszInfoKeyPrefix)-sizeof(WCHAR));
if (pszDesc != NULL)
{
if (fRet = hKey.CreateW(HKEY_CLASSES_ROOT, achIMEKey, NULL, REG_OPTION_NON_VOLATILE, KEY_WRITE) == ERROR_SUCCESS)
{
fRet &= hKey.SetValueW(pszDesc) == ERROR_SUCCESS;
if (pszMenuTextPUI)
fRet &= hKey.SetValueW(pszMenuTextPUI, c_wszMenuTextPUI) == ERROR_SUCCESS;
if (fRet &= hSubKey.CreateW(hKey, c_wszInProcSvr32, NULL, REG_OPTION_NON_VOLATILE, KEY_WRITE) == ERROR_SUCCESS)
{
fRet &= hSubKey.SetValueW(pszPath) == ERROR_SUCCESS;
fRet &= hSubKey.SetValueW(pszModel, c_wszModelName) == ERROR_SUCCESS;
}
}
}
return fRet;
}