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.

357 lines
8.8 KiB

  1. ///////////////////////////////////////////////////////////////////////////////
  2. //
  3. // Copyright 1999 American Power Conversion, All Rights Reserved
  4. //
  5. // Name: upsapplet.cpp
  6. //
  7. // Author: Noel Fegan
  8. //
  9. // Description
  10. // ===========
  11. //
  12. // Revision History
  13. // ================
  14. // 04 May 1999 - [email protected] : Added this comment block.
  15. // 04 May 1999 - [email protected] : Preparing for code inspection
  16. //
  17. #include "upstab.h"
  18. #include <objbase.h>
  19. #include <shlobj.h>
  20. #include <initguid.h>
  21. #include "upsapplet.h"
  22. #pragma hdrstop
  23. extern "C" HINSTANCE g_theInstance = 0;
  24. UINT g_cRefThisDll = 0; // Reference count for this DLL
  25. // {DE5637D2-E12D-11d2-8844-00600844D03F}
  26. DEFINE_GUID(CLSID_ShellExtension,
  27. 0xde5637d2, 0xe12d, 0x11d2, 0x88, 0x44, 0x0, 0x60, 0x8, 0x44, 0xd0, 0x3f);
  28. //
  29. // DllMain is the DLL's entry point.
  30. //
  31. // Input parameters:
  32. // hInstance = Instance handle
  33. // dwReason = Code specifying the reason DllMain was called
  34. // lpReserved = Reserved (do not use)
  35. //
  36. // Returns:
  37. // TRUE if successful, FALSE if not
  38. //
  39. ///////////////////////////////////////////////////////////////////////////////
  40. extern "C" int APIENTRY DllMain (HINSTANCE hInstance, DWORD dwReason,
  41. LPVOID lpReserved)
  42. {
  43. //
  44. // If dwReason is DLL_PROCESS_ATTACH, save the instance handle so it
  45. // can be used again later.
  46. //
  47. if (dwReason == DLL_PROCESS_ATTACH)
  48. {
  49. g_theInstance = hInstance;
  50. DisableThreadLibraryCalls(g_theInstance);
  51. }
  52. return TRUE;
  53. }
  54. /////////////////////////////////////////////////////////////////////////////
  55. // In-process server functions
  56. //
  57. // DllGetClassObject is called by the shell to create a class factory object.
  58. //
  59. // Input parameters:
  60. // rclsid = Reference to class ID specifier
  61. // riid = Reference to interface ID specifier
  62. // ppv = Pointer to location to receive interface pointer
  63. //
  64. // Returns:
  65. // HRESULT code signifying success or failure
  66. //
  67. STDAPI DllGetClassObject (REFCLSID rclsid, REFIID riid, LPVOID *ppv)
  68. {
  69. *ppv = NULL;
  70. //
  71. // Make sure the class ID is CLSID_ShellExtension. Otherwise, the class
  72. // factory doesn't support the object type specified by rclsid.
  73. //
  74. if (!IsEqualCLSID (rclsid, CLSID_ShellExtension))
  75. {
  76. //Error
  77. return ResultFromScode (CLASS_E_CLASSNOTAVAILABLE);
  78. }
  79. //
  80. // Instantiate a class factory object.
  81. //
  82. CClassFactory *pClassFactory = new CClassFactory ();
  83. if (pClassFactory == NULL)
  84. {
  85. //Error
  86. return ResultFromScode (E_OUTOFMEMORY);
  87. }
  88. //
  89. // Get the interface pointer from QueryInterface and copy it to *ppv.
  90. //
  91. HRESULT hr = pClassFactory->QueryInterface (riid, ppv);
  92. pClassFactory->Release ();
  93. return hr;
  94. }
  95. //
  96. // DllCanUnloadNow is called by the shell to find out if the DLL can be
  97. // unloaded. The answer is yes if (and only if) the module reference count
  98. // stored in g_cRefThisDll is 0.
  99. //
  100. // Input parameters:
  101. // None
  102. //
  103. // Returns:
  104. // HRESULT code equal to S_OK if the DLL can be unloaded, S_FALSE if not
  105. //
  106. STDAPI DllCanUnloadNow (void)
  107. {
  108. return ResultFromScode ((g_cRefThisDll == 0) ? S_OK : S_FALSE);
  109. }
  110. /////////////////////////////////////////////////////////////////////////////
  111. // CClassFactory member functions
  112. CClassFactory::CClassFactory ()
  113. {
  114. m_cRef = 1;
  115. g_cRefThisDll++;
  116. }
  117. CClassFactory::~CClassFactory ()
  118. {
  119. g_cRefThisDll--;
  120. }
  121. STDMETHODIMP CClassFactory::QueryInterface (REFIID riid, LPVOID FAR *ppv)
  122. {
  123. if (IsEqualIID (riid, IID_IUnknown)) {
  124. *ppv = (LPUNKNOWN) (LPCLASSFACTORY) this;
  125. m_cRef++;
  126. return NOERROR;
  127. }
  128. else if (IsEqualIID (riid, IID_IClassFactory)) {
  129. *ppv = (LPCLASSFACTORY) this;
  130. m_cRef++;
  131. return NOERROR;
  132. }
  133. else {
  134. *ppv = NULL;
  135. return ResultFromScode (E_NOINTERFACE);
  136. }
  137. }
  138. STDMETHODIMP_(ULONG) CClassFactory::AddRef ()
  139. {
  140. return ++m_cRef;
  141. }
  142. STDMETHODIMP_(ULONG) CClassFactory::Release ()
  143. {
  144. if (--m_cRef == 0)
  145. delete this;
  146. return m_cRef;
  147. }
  148. //
  149. // CreateInstance is called by the shell to create a shell extension object.
  150. //
  151. // Input parameters:
  152. // pUnkOuter = Pointer to controlling unknown
  153. // riid = Reference to interface ID specifier
  154. // ppvObj = Pointer to location to receive interface pointer
  155. //
  156. // Returns:
  157. // HRESULT code signifying success or failure
  158. //
  159. STDMETHODIMP CClassFactory::CreateInstance (LPUNKNOWN pUnkOuter, REFIID riid,
  160. LPVOID FAR *ppvObj)
  161. {
  162. *ppvObj = NULL;
  163. //
  164. // Return an error code if pUnkOuter is not NULL, because we don't
  165. // support aggregation.
  166. //
  167. if (pUnkOuter != NULL)
  168. return ResultFromScode (CLASS_E_NOAGGREGATION);
  169. //
  170. // Instantiate a shell extension object.
  171. //
  172. CShellExtension *pShellExtension = new CShellExtension ();
  173. if (pShellExtension == NULL)
  174. return ResultFromScode (E_OUTOFMEMORY);
  175. // Get the interface pointer from QueryInterface and copy it to *ppvObj.
  176. //
  177. HRESULT hr = pShellExtension->QueryInterface (riid, ppvObj);
  178. pShellExtension->Release ();
  179. return hr;
  180. }
  181. //
  182. // LockServer increments or decrements the DLL's lock count.
  183. //
  184. STDMETHODIMP CClassFactory::LockServer (BOOL fLock)
  185. {
  186. return ResultFromScode (E_NOTIMPL);
  187. }
  188. /////////////////////////////////////////////////////////////////////////////
  189. // CShellExtension member functions
  190. CShellExtension::CShellExtension ()
  191. {
  192. m_cRef = 1;
  193. g_cRefThisDll++;
  194. }
  195. CShellExtension::~CShellExtension ()
  196. {
  197. g_cRefThisDll--;
  198. }
  199. STDMETHODIMP CShellExtension::QueryInterface (REFIID riid, LPVOID FAR *ppv)
  200. {
  201. if (IsEqualIID (riid, IID_IUnknown)) {
  202. *ppv = (LPUNKNOWN) (LPSHELLPROPSHEETEXT) this;
  203. m_cRef++;
  204. return NOERROR;
  205. }
  206. else if (IsEqualIID (riid, IID_IShellPropSheetExt)) {
  207. *ppv = (LPSHELLPROPSHEETEXT) this;
  208. m_cRef++;
  209. return NOERROR;
  210. }
  211. else if (IsEqualIID (riid, IID_IShellExtInit)) {
  212. *ppv = (LPSHELLEXTINIT) this;
  213. m_cRef++;
  214. return NOERROR;
  215. }
  216. else {
  217. *ppv = NULL;
  218. return ResultFromScode (E_NOINTERFACE);
  219. }
  220. }
  221. STDMETHODIMP_(ULONG) CShellExtension::AddRef ()
  222. {
  223. return ++m_cRef;
  224. }
  225. STDMETHODIMP_(ULONG) CShellExtension::Release () {
  226. if (--m_cRef == 0) {
  227. delete this;
  228. }
  229. return(m_cRef);
  230. }
  231. //
  232. // AddPages is called by the shell to give property sheet shell extensions
  233. // the opportunity to add pages to a property sheet before it is displayed.
  234. //
  235. // Input parameters:
  236. // lpfnAddPage = Pointer to function called to add a page
  237. // lParam = lParam parameter to be passed to lpfnAddPage
  238. //
  239. // Returns:
  240. // HRESULT code signifying success or failure
  241. //
  242. STDMETHODIMP CShellExtension::AddPages (LPFNADDPROPSHEETPAGE lpfnAddPage,
  243. LPARAM lParam) {
  244. PROPSHEETPAGE psp;
  245. HPROPSHEETPAGE hUPSPage = NULL;
  246. HMODULE hModule = GetUPSModuleHandle();
  247. ZeroMemory(&psp, sizeof(psp));
  248. psp.dwSize = sizeof(psp);
  249. psp.dwFlags = PSP_USEREFPARENT;
  250. psp.hInstance = hModule;
  251. psp.pszTemplate = TEXT("IDD_UPS_EXT");
  252. psp.pfnDlgProc = UPSMainPageProc;
  253. psp.pcRefParent = &g_cRefThisDll;
  254. hUPSPage = CreatePropertySheetPage (&psp);
  255. //
  256. // Add the pages to the property sheet.
  257. //
  258. if (hUPSPage != NULL) {
  259. if (!lpfnAddPage(hUPSPage, lParam)) {
  260. DestroyPropertySheetPage(hUPSPage);
  261. }
  262. }
  263. return(NOERROR);
  264. }
  265. //
  266. // ReplacePage is called by the shell to give control panel extensions the
  267. // opportunity to replace control panel property sheet pages. It is never
  268. // called for conventional property sheet extensions, so we simply return
  269. // a failure code if called.
  270. //
  271. // Input parameters:
  272. // uPageID = Page to replace
  273. // lpfnReplaceWith = Pointer to function called to replace a page
  274. // lParam = lParam parameter to be passed to lpfnReplaceWith
  275. //
  276. // Returns:
  277. // HRESULT code signifying success or failure
  278. //
  279. STDMETHODIMP CShellExtension::ReplacePage (UINT uPageID,
  280. LPFNADDPROPSHEETPAGE lpfnReplaceWith, LPARAM lParam)
  281. {
  282. return ResultFromScode (E_FAIL);
  283. }
  284. //
  285. // Initialize is called by the shell to initialize a shell extension.
  286. //
  287. // Input parameters:
  288. // pidlFolder = Pointer to ID list identifying parent folder
  289. // lpdobj = Pointer to IDataObject interface for selected object(s)
  290. // hKeyProgId = Registry key handle
  291. //
  292. // Returns:
  293. // HRESULT code signifying success or failure
  294. //
  295. STDMETHODIMP CShellExtension::Initialize (LPCITEMIDLIST pidlFolder,
  296. LPDATAOBJECT lpdobj, HKEY hKeyProgID)
  297. {
  298. return ResultFromScode (NO_ERROR);
  299. }