Source code of Windows XP (NT5)
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.

276 lines
6.2 KiB

  1. // oledll.cpp
  2. //
  3. // Copyright (c) 1997-2000 Microsoft Corporation. All rights reserved.
  4. //
  5. #include <objbase.h>
  6. #include "debug.h"
  7. #include <iostream.h>
  8. #include "oledll.h"
  9. static const TCHAR g_szCLSID[] = TEXT("CLSID");
  10. static const TCHAR g_szCLSIDSlash[] = TEXT("CLSID\\");
  11. static const TCHAR g_szInProc32[] = TEXT("InProcServer32");
  12. static const TCHAR g_szProgIDKey[] = TEXT("ProgID");
  13. static const TCHAR g_szVerIndProgIDKey[] = TEXT("VersionIndependentProgID");
  14. static const TCHAR g_szCurVer[] = TEXT("CurVer");
  15. static const TCHAR g_szThreadingModel[] = TEXT("ThreadingModel");
  16. static const TCHAR g_szBoth[] = TEXT("Both");
  17. static const int CLSID_STRING_SIZE = 39;
  18. static LONG RegSetDefValue(LPCTSTR pstrKey, LPCTSTR pstrSubkey, LPCTSTR pstrValueName, LPCTSTR pstrValue);
  19. static void RegRemoveSubtree(HKEY hk, LPCTSTR pstrChild);
  20. STDAPI
  21. RegisterServer(HMODULE hModule,
  22. const CLSID &clsid,
  23. const TCHAR *szFriendlyName,
  24. const TCHAR *szVerIndProgID,
  25. const TCHAR *szProgID)
  26. {
  27. TCHAR szCLSID[CLSID_STRING_SIZE];
  28. HRESULT hr;
  29. LONG lr;
  30. hr = CLSIDToStr(clsid, szCLSID, sizeof(szCLSID));
  31. if (!SUCCEEDED(hr)) {
  32. return hr;
  33. }
  34. TCHAR szClsKey[256];
  35. lstrcpy(szClsKey, g_szCLSIDSlash);
  36. lstrcat(szClsKey, szCLSID);
  37. TCHAR szModule[512];
  38. lr = ::GetModuleFileName(hModule, szModule, sizeof(szModule));
  39. assert(lr);
  40. lr = 0;
  41. lr |= RegSetDefValue(szClsKey, NULL, NULL, szFriendlyName);
  42. lr |= RegSetDefValue(szClsKey, g_szInProc32, NULL, szModule);
  43. lr |= RegSetDefValue(szClsKey, g_szInProc32, g_szThreadingModel, g_szBoth);
  44. lr |= RegSetDefValue(szClsKey, g_szProgIDKey, NULL, szProgID);
  45. lr |= RegSetDefValue(szClsKey, g_szVerIndProgIDKey, NULL, szVerIndProgID);
  46. lr |= RegSetDefValue(szVerIndProgID, NULL, NULL, szFriendlyName);
  47. lr |= RegSetDefValue(szVerIndProgID, g_szCLSID, NULL, szCLSID);
  48. lr |= RegSetDefValue(szVerIndProgID, g_szCurVer, NULL, szProgID);
  49. lr |= RegSetDefValue(szProgID, NULL, NULL, szFriendlyName);
  50. lr |= RegSetDefValue(szProgID, g_szCLSID, NULL, szCLSID);
  51. #if 0
  52. if (lr) {
  53. UnregisterServer(clsid,
  54. szFriendlyName,
  55. szVerIndProgID,
  56. szProgID);
  57. // ???
  58. //
  59. return S_OK;
  60. }
  61. #endif
  62. return S_OK;
  63. }
  64. STDAPI
  65. UnregisterServer(const CLSID &clsid,
  66. const TCHAR *szFriendlyName,
  67. const TCHAR *szVerIndProgID,
  68. const TCHAR *szProgID)
  69. {
  70. TCHAR szCLSID[CLSID_STRING_SIZE];
  71. HRESULT hr;
  72. hr = CLSIDToStr(clsid, szCLSID, sizeof(szCLSID));
  73. if (!SUCCEEDED(hr)) {
  74. return hr;
  75. }
  76. TCHAR szClsKey[256];
  77. lstrcpy(szClsKey, g_szCLSIDSlash);
  78. lstrcat(szClsKey, szCLSID);
  79. RegRemoveSubtree(HKEY_CLASSES_ROOT, szClsKey);
  80. RegRemoveSubtree(HKEY_CLASSES_ROOT, szVerIndProgID);
  81. RegRemoveSubtree(HKEY_CLASSES_ROOT, szProgID);
  82. return S_OK;
  83. }
  84. BOOL
  85. GetCLSIDRegValue(const CLSID &clsid,
  86. const TCHAR *szKey,
  87. LPVOID pValue,
  88. LPDWORD pcbValue)
  89. {
  90. TCHAR szCLSID[CLSID_STRING_SIZE];
  91. HRESULT hr;
  92. HKEY hk;
  93. DWORD dw;
  94. hr = CLSIDToStr(clsid, szCLSID, sizeof(szCLSID));
  95. if (!SUCCEEDED(hr)) {
  96. return FALSE;
  97. }
  98. TCHAR szClsKey[256];
  99. lstrcpy(szClsKey, g_szCLSIDSlash);
  100. lstrcat(szClsKey, szCLSID);
  101. lstrcat(szClsKey, TEXT("\\"));
  102. if (szKey)
  103. {
  104. lstrcat(szClsKey, szKey);
  105. }
  106. if (RegOpenKeyEx(HKEY_CLASSES_ROOT,
  107. szClsKey,
  108. 0,
  109. KEY_READ,
  110. &hk)) {
  111. return FALSE;
  112. }
  113. if (RegQueryValueEx(hk,
  114. NULL,
  115. NULL,
  116. &dw,
  117. (LPBYTE)pValue,
  118. pcbValue)) {
  119. RegCloseKey(hk);
  120. return FALSE;
  121. }
  122. RegCloseKey(hk);
  123. return TRUE;
  124. }
  125. HRESULT
  126. CLSIDToStr(const CLSID &clsid,
  127. TCHAR *szStr,
  128. int cbStr)
  129. {
  130. // XXX What to return here?
  131. //
  132. assert(cbStr >= CLSID_STRING_SIZE);
  133. LPOLESTR wszCLSID = NULL;
  134. HRESULT hr = StringFromCLSID(clsid, &wszCLSID);
  135. if (!SUCCEEDED(hr)) {
  136. return hr;
  137. }
  138. #ifdef UNICODE
  139. lstrcpy(szStr, wszCLSID);
  140. #else
  141. // Covert from wide characters to non-wide.
  142. wcstombs(szStr, wszCLSID, cbStr);
  143. #endif
  144. // Free memory.
  145. CoTaskMemFree(wszCLSID);
  146. return S_OK;
  147. }
  148. HRESULT
  149. StrToCLSID(TCHAR *szStr,
  150. CLSID &clsid,
  151. int cbStr)
  152. {
  153. #ifdef UNICODE
  154. return CLSIDFromString(szStr, &clsid);
  155. #else
  156. WCHAR wsz[512];
  157. if (cbStr > 512)
  158. {
  159. cbStr = 512;
  160. }
  161. mbstowcs(wsz, szStr, cbStr);
  162. return CLSIDFromString(wsz, &clsid);
  163. #endif
  164. }
  165. static LONG
  166. RegSetDefValue(LPCTSTR pstrKey,
  167. LPCTSTR pstrSubkey,
  168. LPCTSTR pstrValueName,
  169. LPCTSTR pstrValue)
  170. {
  171. HKEY hk;
  172. LONG lr;
  173. TCHAR sz[1024];
  174. LPCTSTR pstr;
  175. if (!pstrSubkey) {
  176. pstr = pstrKey;
  177. } else {
  178. lstrcpy(sz, pstrKey);
  179. lstrcat(sz, TEXT("\\"));
  180. lstrcat(sz, pstrSubkey);
  181. pstr = sz;
  182. }
  183. lr = RegCreateKeyEx(HKEY_CLASSES_ROOT,
  184. pstr,
  185. 0,
  186. NULL,
  187. REG_OPTION_NON_VOLATILE,
  188. KEY_ALL_ACCESS,
  189. NULL,
  190. &hk,
  191. NULL);
  192. if (lr) {
  193. return lr;
  194. }
  195. lr = RegSetValueEx(hk,
  196. pstrValueName,
  197. 0,
  198. REG_SZ,
  199. (CONST BYTE*)pstrValue,
  200. 1+lstrlen(pstrValue));
  201. RegCloseKey(hk);
  202. return lr;
  203. }
  204. static void
  205. RegRemoveSubtree(HKEY hk,
  206. LPCTSTR pstrChild)
  207. {
  208. LONG lResult;
  209. HKEY hkChild;
  210. lResult = RegOpenKeyEx(hk,
  211. pstrChild,
  212. 0,
  213. KEY_ALL_ACCESS,
  214. &hkChild);
  215. if (lResult) {
  216. return;
  217. }
  218. #ifndef UNDER_CE // CE doesn't support RegEnumKey()
  219. TCHAR szSubkey[256];
  220. // NOTE: Unlike regular enumeration, we always grab the 0th item
  221. // and delete it.
  222. //
  223. while (!RegEnumKey(hkChild, 0, szSubkey, sizeof(szSubkey))) {
  224. RegRemoveSubtree(hkChild, szSubkey);
  225. }
  226. #endif
  227. RegCloseKey(hkChild);
  228. RegDeleteKey(hk, pstrChild);
  229. }