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.

522 lines
15 KiB

  1. /////////////////////////////////////////////////////////////////////////////
  2. //
  3. // THIS CODE AND INFORMATION IS PROVIDED "AS IS" WITHOUT WARRANTY OF
  4. // ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO
  5. // THE IMPLIED WARRANTIES OF MERCHANTABILITY AND/OR FITNESS FOR A
  6. // PARTICULAR PURPOSE.
  7. //
  8. // Copyright 1998 Microsoft Corporation. All Rights Reserved.
  9. //
  10. // Author: Scott Roberts, Microsoft Developer Support - Internet Client SDK
  11. //
  12. // Portions of this code were taken from the bandobj sample that comes
  13. // with the Internet Client SDK for Internet Explorer 4.0x
  14. //
  15. // BLFrame.cpp : Contains DLLMain and standard COM object functions.
  16. /////////////////////////////////////////////////////////////////////////////
  17. #include "pch.hxx"
  18. #include <shlwapi.h>
  19. #include <shlwapip.h>
  20. #define ARRAYSIZE(x) (sizeof(x)/sizeof(x[0]))
  21. #include <atlimpl.cpp>
  22. #include <atlctl.cpp>
  23. #include <atlwinx.cpp>
  24. #include <ole2.h>
  25. #include <comcat.h>
  26. #include <olectl.h>
  27. #include "ClsFact.h"
  28. #include "resource.h"
  29. #include "msoert.h"
  30. #include "shared.h"
  31. // #include "demand.h"
  32. static const char c_szShlwapiDll[] = "shlwapi.dll";
  33. static const char c_szDllGetVersion[] = "DllGetVersion";
  34. // This part is only done once
  35. // If you need to use the GUID in another file, just include Guid.h
  36. //#pragma data_seg(".text")
  37. #define INITGUID
  38. #include <initguid.h>
  39. #include <shlguid.h>
  40. #include "Guid.h"
  41. //#pragma data_seg()
  42. // HINSTANCE LoadLangDll(HINSTANCE hInstCaller, LPCSTR szDllName, BOOL fNT);
  43. const TCHAR c_szBlCtlResDll[] = "iecontlc.dll";
  44. extern "C" BOOL WINAPI DllMain(HINSTANCE, DWORD, LPVOID);
  45. BOOL RegisterServer(CLSID, LPTSTR);
  46. BOOL RegisterComCat(CLSID, CATID);
  47. BOOL UnRegisterServer(CLSID);
  48. BOOL UnRegisterComCat(CLSID, CATID);
  49. HINSTANCE g_hLocRes;
  50. HINSTANCE g_OrgInst = NULL;
  51. LONG g_cDllRefCount;
  52. CComModule _Module;
  53. BEGIN_OBJECT_MAP(ObjectMap)
  54. OBJECT_ENTRY(CLSID_IEMsgAb, CIEMsgAb)
  55. END_OBJECT_MAP()
  56. typedef struct
  57. {
  58. HKEY hRootKey;
  59. LPTSTR szSubKey; // TCHAR szSubKey[MAX_PATH];
  60. LPTSTR lpszValueName;
  61. LPTSTR szData; // TCHAR szData[MAX_PATH];
  62. } DOREGSTRUCT, *LPDOREGSTRUCT;
  63. typedef HINSTANCE (STDAPICALLTYPE *PFNMLLOADLIBARY)(LPCSTR lpLibFileName, HMODULE hModule, DWORD dwCrossCodePage);
  64. HINSTANCE IELoadLangDll(HINSTANCE hInstCaller, LPCSTR szDllName, BOOL fNT)
  65. {
  66. char szPath[MAX_PATH];
  67. HINSTANCE hinstShlwapi;
  68. PFNMLLOADLIBARY pfn;
  69. DLLGETVERSIONPROC pfnVersion;
  70. int iEnd;
  71. DLLVERSIONINFO info;
  72. HINSTANCE hInst = NULL;
  73. hinstShlwapi = LoadLibrary(c_szShlwapiDll);
  74. if (hinstShlwapi != NULL)
  75. {
  76. pfnVersion = (DLLGETVERSIONPROC)GetProcAddress(hinstShlwapi, c_szDllGetVersion);
  77. if (pfnVersion != NULL)
  78. {
  79. info.cbSize = sizeof(DLLVERSIONINFO);
  80. if (SUCCEEDED(pfnVersion(&info)))
  81. {
  82. if (info.dwMajorVersion >= 5)
  83. {
  84. pfn = (PFNMLLOADLIBARY)GetProcAddress(hinstShlwapi, MAKEINTRESOURCE(377));
  85. if (pfn != NULL)
  86. hInst = pfn(szDllName, hInstCaller, (ML_CROSSCODEPAGE));
  87. }
  88. }
  89. }
  90. FreeLibrary(hinstShlwapi);
  91. }
  92. if ((NULL == hInst) && (GetModuleFileName(hInstCaller, szPath, ARRAYSIZE(szPath))))
  93. {
  94. PathRemoveFileSpec(szPath);
  95. iEnd = lstrlen(szPath);
  96. szPath[iEnd++] = '\\';
  97. StrCpyN(&szPath[iEnd], szDllName, ARRAYSIZE(szPath)-iEnd);
  98. hInst = LoadLibrary(szPath);
  99. }
  100. AssertSz(hInst, "Failed to LoadLibrary Lang Dll");
  101. return(hInst);
  102. }
  103. // CComModule _Module;
  104. IMalloc *g_pMalloc=NULL;
  105. extern "C" BOOL WINAPI DllMain(HINSTANCE hInstance, DWORD dwReason, LPVOID lpReserved)
  106. {
  107. switch(dwReason)
  108. {
  109. case DLL_PROCESS_ATTACH:
  110. CoGetMalloc(1, &g_pMalloc);
  111. // Get Resources from Lang DLL
  112. g_OrgInst = hInstance;
  113. g_hLocRes = IELoadLangDll(hInstance, c_szBlCtlResDll, TRUE);
  114. if(g_hLocRes == NULL)
  115. {
  116. _ASSERT(FALSE);
  117. return FALSE;
  118. }
  119. _Module.Init(ObjectMap, hInstance);
  120. // InitDemandLoadedLibs();
  121. DisableThreadLibraryCalls(hInstance);
  122. break;
  123. case DLL_PROCESS_DETACH:
  124. // FreeDemandLoadedLibs();
  125. _Module.Term();
  126. SafeRelease(g_pMalloc);
  127. break;
  128. }
  129. return TRUE;
  130. }
  131. STDAPI DllCanUnloadNow(void)
  132. {
  133. return (g_cDllRefCount ? S_FALSE : S_OK);
  134. }
  135. STDAPI DllGetClassObject(REFCLSID rclsid, REFIID riid, LPVOID* ppv)
  136. {
  137. *ppv = NULL;
  138. HRESULT hr = E_FAIL;
  139. // If we don't support this classid, return the proper error code
  140. if (!IsEqualCLSID(rclsid, CLSID_BLHost) && !IsEqualCLSID(rclsid, CLSID_IEMsgAb) )
  141. return CLASS_E_CLASSNOTAVAILABLE;
  142. if(IsEqualCLSID(rclsid, CLSID_BLHost))
  143. {
  144. // Create a CClassFactory object and check it for validity
  145. CClassFactory* pClassFactory = new CClassFactory(rclsid);
  146. if (NULL == pClassFactory)
  147. return E_OUTOFMEMORY;
  148. // QI for the requested interface
  149. hr = pClassFactory->QueryInterface(riid, ppv);
  150. // Call Release to decement the ref count - creating the object set it to one
  151. // and QueryInterface incremented it - since its being used externally (not by
  152. // us), we only want the ref count to be 1
  153. pClassFactory->Release();
  154. }
  155. else if(IsEqualCLSID(rclsid, CLSID_IEMsgAb))
  156. return _Module.GetClassObject(rclsid, riid, ppv);
  157. return hr;
  158. }
  159. STDAPI DllRegisterServer(void)
  160. {
  161. TCHAR szTitle[256];
  162. // Register the explorer bar object.
  163. if(!ANSI_AthLoadString(idsTitle, szTitle, ARRAYSIZE(szTitle)))
  164. {
  165. _ASSERT(FALSE);
  166. szTitle[0] = '\0';
  167. }
  168. if (!RegisterServer(CLSID_BLHost, szTitle))
  169. return SELFREG_E_CLASS;
  170. // Register the Component Categories for the explorer bar object.
  171. RegisterComCat(CLSID_BLHost, CATID_InfoBand); // ignore error in this case
  172. // registers IEMsgAb object, typelib and all interfaces in typelib
  173. _Module.RegisterServer(TRUE);
  174. return S_OK;
  175. }
  176. STDAPI DllUnregisterServer(void)
  177. {
  178. // Register the Component Categories for the explorer bar object.
  179. UnRegisterComCat(CLSID_BLHost, CATID_InfoBand); // ignore error in this case
  180. // Register the explorer bar object.
  181. if (!UnRegisterServer(CLSID_BLHost))
  182. return SELFREG_E_CLASS;
  183. _Module.UnregisterServer();
  184. return S_OK;
  185. }
  186. BOOL RegisterServer(CLSID clsid, LPTSTR lpszTitle)
  187. {
  188. int i;
  189. HKEY hKey;
  190. LRESULT lResult;
  191. DWORD dwDisp;
  192. TCHAR szSubKey[MAX_PATH];
  193. TCHAR szCLSID[MAX_PATH];
  194. TCHAR szBlFrameCLSID[MAX_PATH];
  195. TCHAR szModule[MAX_PATH];
  196. LPWSTR pwsz;
  197. // Get the CLSID in string form
  198. StringFromIID(clsid, &pwsz);
  199. if (pwsz)
  200. {
  201. #ifdef UNICODE
  202. StrCpyN(szBlFrameCLSID, pwsz, ARRAYSIZE(szBlFrameCLSID));
  203. #else
  204. WideCharToMultiByte(CP_ACP, 0, pwsz, -1, szBlFrameCLSID,
  205. ARRAYSIZE(szBlFrameCLSID), NULL, NULL);
  206. #endif
  207. // Free the string
  208. LPMALLOC pMalloc;
  209. CoGetMalloc(1, &pMalloc);
  210. pMalloc->Free(pwsz);
  211. pMalloc->Release();
  212. }
  213. // Get this app's path and file name
  214. GetModuleFileName(g_OrgInst, szModule, ARRAYSIZE(szModule));
  215. DOREGSTRUCT ClsidEntries[] =
  216. {
  217. HKEY_CLASSES_ROOT, TEXT("CLSID\\%s"),
  218. NULL, lpszTitle,
  219. HKEY_CLASSES_ROOT, TEXT("CLSID\\%s\\InprocServer32"),
  220. NULL, szModule,
  221. HKEY_CLASSES_ROOT, TEXT("CLSID\\%s\\InprocServer32"),
  222. TEXT("ThreadingModel"), TEXT("Apartment"),
  223. NULL, NULL, NULL, NULL
  224. };
  225. // Register the CLSID entries
  226. for (i = 0; ClsidEntries[i].hRootKey; i++)
  227. {
  228. // Create the sub key string - for this case, insert
  229. // the file extension
  230. //
  231. wnsprintf(szSubKey, ARRAYSIZE(szSubKey), ClsidEntries[i].szSubKey, szBlFrameCLSID);
  232. lResult = RegCreateKeyEx(ClsidEntries[i].hRootKey, szSubKey,
  233. 0, NULL, REG_OPTION_NON_VOLATILE,
  234. KEY_WRITE, NULL, &hKey, &dwDisp);
  235. if (ERROR_SUCCESS == lResult)
  236. {
  237. TCHAR szData[MAX_PATH];
  238. // If necessary, create the value string
  239. wnsprintf(szData, ARRAYSIZE(szData), ClsidEntries[i].szData, szModule);
  240. lResult = RegSetValueEx(hKey, ClsidEntries[i].lpszValueName,
  241. 0, REG_SZ, (LPBYTE)szData,
  242. lstrlen(szData) + 1);
  243. RegCloseKey(hKey);
  244. if (ERROR_SUCCESS != lResult)
  245. return FALSE;
  246. }
  247. else
  248. {
  249. return FALSE;
  250. }
  251. }
  252. // Create the Registry key entry and values for the
  253. // toolbar button.
  254. //
  255. StringFromIID(CLSID_BlFrameButton, &pwsz);
  256. if (!pwsz)
  257. return TRUE;
  258. #ifdef UNICODE
  259. StrCpyN(szCLSID, pwsz, ARRAYSIZE(szCLSID));
  260. #else
  261. WideCharToMultiByte(CP_ACP, 0, pwsz, -1, szCLSID,
  262. ARRAYSIZE(szCLSID), NULL, NULL);
  263. #endif
  264. // Free the string
  265. LPMALLOC pMalloc;
  266. CoGetMalloc(1, &pMalloc);
  267. pMalloc->Free(pwsz);
  268. pMalloc->Release();
  269. wnsprintf(szSubKey, ARRAYSIZE(szSubKey), "Software\\Microsoft\\Internet Explorer\\Extensions\\%s",
  270. szCLSID);
  271. lResult = RegCreateKeyEx(HKEY_LOCAL_MACHINE, szSubKey,
  272. 0, NULL, REG_OPTION_NON_VOLATILE,
  273. KEY_WRITE, NULL, &hKey, &dwDisp);
  274. if (ERROR_SUCCESS == lResult)
  275. {
  276. TCHAR szData[MAX_PATH];
  277. // Create the value strings
  278. //
  279. // Register the explorer bar object.
  280. OSVERSIONINFO OSInfo;
  281. BOOL fWhistler = FALSE;
  282. OSInfo.dwOSVersionInfoSize = sizeof(OSVERSIONINFO);
  283. GetVersionEx(&OSInfo);
  284. if((OSInfo.dwPlatformId == VER_PLATFORM_WIN32_NT) && (OSInfo.dwMajorVersion >= 5) &&
  285. (OSInfo.dwMinorVersion >= 1))
  286. fWhistler = TRUE;
  287. #ifdef NEED // Bug 28254
  288. StrCpyN(szData, "Yes", ARRAYSIZE(szData));
  289. RegSetValueEx(hKey, TEXT("Default Visible"),
  290. 0, REG_SZ, (LPBYTE)szData,
  291. lstrlen(szData) + 1);
  292. #endif
  293. TCHAR szPath[MAX_PATH];
  294. HMODULE hModule;
  295. hModule = GetModuleHandle(TEXT("iecont.dll"));
  296. GetModuleFileName(hModule, szPath, MAX_PATH);
  297. wnsprintf(szData, ARRAYSIZE(szData), "%s,%d", szPath, fWhistler ? IDI_WHISTICON : IDI_HOTICON);
  298. RegSetValueEx(hKey, TEXT("HotIcon"),
  299. 0, REG_SZ, (LPBYTE)szData,
  300. lstrlen(szData) + 1);
  301. wnsprintf(szData, ARRAYSIZE(szData), "%s,%d", szPath, fWhistler ? IDI_WHISTICON : IDI_ICON);
  302. RegSetValueEx(hKey, TEXT("Icon"),
  303. 0, REG_SZ, (LPBYTE)szData,
  304. lstrlen(szData) + 1);
  305. StrCpyN(szData, "{E0DD6CAB-2D10-11D2-8F1A-0000F87ABD16}", ARRAYSIZE(szData));
  306. RegSetValueEx(hKey, TEXT("CLSID"),
  307. 0, REG_SZ, (LPBYTE)szData,
  308. lstrlen(szData) + 1);
  309. wnsprintf(szData, ARRAYSIZE(szData), "%s", szBlFrameCLSID);
  310. RegSetValueEx(hKey, TEXT("BandCLSID"),
  311. 0, REG_SZ, (LPBYTE)szData,
  312. lstrlen(szData) + 1);
  313. // SHGetWebFolderFilePath(TEXT("iecontlc.dll"), szPath, ARRAYSIZE(szPath));
  314. wnsprintf(szData, ARRAYSIZE(szData), "@iecontlc.dll,-%d",idsButtontext);
  315. RegSetValueEx(hKey, TEXT("ButtonText"),
  316. 0, REG_SZ, (LPBYTE)szData,
  317. lstrlen(szData) + 1);
  318. wnsprintf(szData, ARRAYSIZE(szData), "@iecontlc.dll,-%d",idsTitle);
  319. RegSetValueEx(hKey, TEXT("MenuText"),
  320. 0, REG_SZ, (LPBYTE)szData,
  321. lstrlen(szData) + 1);
  322. RegCloseKey(hKey);
  323. }
  324. return TRUE;
  325. }
  326. BOOL RegisterComCat(CLSID clsid, CATID CatID)
  327. {
  328. ICatRegister* pcr;
  329. HRESULT hr = S_OK ;
  330. CoInitialize(NULL);
  331. hr = CoCreateInstance(CLSID_StdComponentCategoriesMgr,
  332. NULL,
  333. CLSCTX_INPROC_SERVER,
  334. IID_ICatRegister,
  335. (LPVOID*)&pcr);
  336. if (SUCCEEDED(hr))
  337. {
  338. hr = pcr->RegisterClassImplCategories(clsid, 1, &CatID);
  339. pcr->Release();
  340. }
  341. CoUninitialize();
  342. return SUCCEEDED(hr);
  343. }
  344. BOOL UnRegisterServer(CLSID clsid)
  345. {
  346. TCHAR szSubKey[MAX_PATH];
  347. TCHAR szCLSID[MAX_PATH];
  348. LPWSTR pwsz;
  349. // Get the CLSID in string form
  350. StringFromIID(clsid, &pwsz);
  351. if (pwsz)
  352. {
  353. #ifdef UNICODE
  354. StrCpyN(szCLSID, pwsz, ARRAYSIZE(szCLSID));
  355. #else
  356. WideCharToMultiByte(CP_ACP, 0, pwsz, -1, szCLSID,
  357. ARRAYSIZE(szCLSID), NULL, NULL);
  358. #endif
  359. // Free the string
  360. LPMALLOC pMalloc;
  361. CoGetMalloc(1, &pMalloc);
  362. pMalloc->Free(pwsz);
  363. pMalloc->Release();
  364. }
  365. DOREGSTRUCT ClsidEntries[] =
  366. {
  367. HKEY_CLASSES_ROOT, TEXT("CLSID\\%s\\InprocServer32"),
  368. NULL, NULL,
  369. //
  370. // Remove the "Implemented Categories" key, just in case
  371. // UnRegisterClassImplCategories does not remove it
  372. //
  373. HKEY_CLASSES_ROOT, TEXT("CLSID\\%s\\Implemented Categories"),
  374. NULL, NULL,
  375. HKEY_CLASSES_ROOT, TEXT("CLSID\\%s"), NULL, NULL,
  376. NULL, NULL, NULL, NULL
  377. };
  378. // Delete the CLSID entries
  379. for (int i = 0; ClsidEntries[i].hRootKey; i++)
  380. {
  381. wnsprintf(szSubKey, ARRAYSIZE(szSubKey), ClsidEntries[i].szSubKey, szCLSID);
  382. RegDeleteKey(ClsidEntries[i].hRootKey, szSubKey);
  383. }
  384. // Delete the button information
  385. //
  386. StringFromIID(CLSID_BlFrameButton, &pwsz);
  387. if (!pwsz)
  388. return TRUE;
  389. #ifdef UNICODE
  390. StrCpyN(szCLSID, pwsz, ARRAYSIZE(szCLSID));
  391. #else
  392. WideCharToMultiByte(CP_ACP, 0, pwsz, -1, szCLSID,
  393. ARRAYSIZE(szCLSID), NULL, NULL);
  394. #endif
  395. // Free the string
  396. LPMALLOC pMalloc;
  397. CoGetMalloc(1, &pMalloc);
  398. pMalloc->Free(pwsz);
  399. pMalloc->Release();
  400. wnsprintf(szSubKey, ARRAYSIZE(szSubKey), "Software\\Microsoft\\Internet Explorer\\Extensions\\%s", szCLSID);
  401. RegDeleteKey(HKEY_LOCAL_MACHINE, szSubKey);
  402. return TRUE;
  403. }
  404. BOOL UnRegisterComCat(CLSID clsid, CATID CatID)
  405. {
  406. ICatRegister* pcr;
  407. HRESULT hr = S_OK ;
  408. CoInitialize(NULL);
  409. hr = CoCreateInstance(CLSID_StdComponentCategoriesMgr,
  410. NULL,
  411. CLSCTX_INPROC_SERVER,
  412. IID_ICatRegister,
  413. (LPVOID*)&pcr);
  414. if (SUCCEEDED(hr))
  415. {
  416. hr = pcr->UnRegisterClassImplCategories(clsid, 1, &CatID);
  417. pcr->Release();
  418. }
  419. CoUninitialize();
  420. return SUCCEEDED(hr);
  421. }