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.

290 lines
7.2 KiB

  1. //+-------------------------------------------------------------------------
  2. //
  3. // Microsoft Windows
  4. // Copyright (C) Microsoft Corporation, 1996-1998
  5. //
  6. // File: ClassFac.cxx
  7. //
  8. // Contents: Class factory for admin COM object
  9. //
  10. // History: 26-Nov-1996 KyleP Created
  11. //
  12. //--------------------------------------------------------------------------
  13. #include <pch.cxx>
  14. #pragma hdrstop
  15. #include <classid.hxx>
  16. #include <classfac.hxx>
  17. #include <snapin.hxx>
  18. //
  19. // Global variables
  20. //
  21. long gulcInstances = 0;
  22. //+-------------------------------------------------------------------------
  23. //
  24. // Method: CCIAdminCF::CCIAdminCF
  25. //
  26. // Synopsis: CI MMC snap-in class factory constructor
  27. //
  28. // History: 26-Nov-1996 KyleP Created
  29. //
  30. //--------------------------------------------------------------------------
  31. CCIAdminCF::CCIAdminCF()
  32. {
  33. _uRefs = 1;
  34. InterlockedIncrement( &gulcInstances );
  35. }
  36. //+-------------------------------------------------------------------------
  37. //
  38. // Method: CCIAdminCF::~CCIAdminCF
  39. //
  40. // Synopsis: Text IFilter class factory constructor
  41. //
  42. // History: 26-Nov-1996 KyleP Created
  43. // History: 23-Feb-1994 KyleP Created
  44. //
  45. //--------------------------------------------------------------------------
  46. CCIAdminCF::~CCIAdminCF()
  47. {
  48. InterlockedDecrement( &gulcInstances );
  49. }
  50. //+-------------------------------------------------------------------------
  51. //
  52. // Method: CCIAdminCF::QueryInterface
  53. //
  54. // Synopsis: Rebind to other interface
  55. //
  56. // Arguments: [riid] -- IID of new interface
  57. // [ppvObject] -- New interface * returned here
  58. //
  59. // Returns: S_OK if bind succeeded, E_NOINTERFACE if bind failed
  60. //
  61. // History: 26-Nov-1996 KyleP Created
  62. //
  63. //--------------------------------------------------------------------------
  64. SCODE STDMETHODCALLTYPE CCIAdminCF::QueryInterface( REFIID riid,
  65. void ** ppvObject )
  66. {
  67. SCODE sc = S_OK;
  68. if ( 0 == ppvObject )
  69. return E_INVALIDARG;
  70. if ( IID_IClassFactory == riid )
  71. *ppvObject = (IUnknown *)(IClassFactory *)this;
  72. else if ( IID_IUnknown == riid )
  73. *ppvObject = (IUnknown *)(IClassFactory *)this;
  74. else
  75. sc = E_NOINTERFACE;
  76. if ( SUCCEEDED( sc ) )
  77. AddRef();
  78. return sc;
  79. } //QueryInterface
  80. //+-------------------------------------------------------------------------
  81. //
  82. // Method: CCIAdminCF::AddRef
  83. //
  84. // Synopsis: Increments refcount
  85. //
  86. // History: 23-Feb-1994 KyleP Created
  87. // History: 26-Nov-1996 KyleP Created
  88. //
  89. //--------------------------------------------------------------------------
  90. ULONG STDMETHODCALLTYPE CCIAdminCF::AddRef()
  91. {
  92. return InterlockedIncrement( &_uRefs );
  93. }
  94. //+-------------------------------------------------------------------------
  95. //
  96. // Method: CCIAdminCF::Release
  97. //
  98. // Synopsis: Decrement refcount. Delete if necessary.
  99. //
  100. // History: 23-Feb-1994 KyleP Created
  101. // History: 26-Nov-1996 KyleP Created
  102. //
  103. //--------------------------------------------------------------------------
  104. ULONG STDMETHODCALLTYPE CCIAdminCF::Release()
  105. {
  106. unsigned long uTmp = InterlockedDecrement( &_uRefs );
  107. if ( 0 == uTmp )
  108. delete this;
  109. return uTmp;
  110. }
  111. //+-------------------------------------------------------------------------
  112. //
  113. // Method: CCIAdminCF::CreateInstance
  114. //
  115. // Synopsis: Creates new snapin data object
  116. //
  117. // Arguments: [pUnkOuter] -- 'Outer' IUnknown
  118. // [riid] -- Interface to bind
  119. // [ppvObject] -- Interface returned here
  120. //
  121. // History: 26-Nov-1996 KyleP Created
  122. //
  123. //--------------------------------------------------------------------------
  124. SCODE STDMETHODCALLTYPE CCIAdminCF::CreateInstance( IUnknown * pUnkOuter,
  125. REFIID riid,
  126. void * * ppvObject )
  127. {
  128. IUnknown * pIUnk = 0;
  129. SCODE sc = S_OK;
  130. TRANSLATE_EXCEPTIONS;
  131. TRY
  132. {
  133. pIUnk = (IUnknown *)(IComponent *)new CCISnapinData();
  134. sc = pIUnk->QueryInterface( riid , ppvObject );
  135. if( SUCCEEDED(sc) )
  136. pIUnk->Release(); // Release extra refcount from QueryInterface
  137. }
  138. CATCH(CException, e)
  139. {
  140. Win4Assert( 0 == pIUnk );
  141. switch( e.GetErrorCode() )
  142. {
  143. case E_OUTOFMEMORY:
  144. sc = (E_OUTOFMEMORY);
  145. break;
  146. default:
  147. sc = (E_UNEXPECTED);
  148. }
  149. }
  150. END_CATCH;
  151. UNTRANSLATE_EXCEPTIONS;
  152. return (sc);
  153. }
  154. //+-------------------------------------------------------------------------
  155. //
  156. // Method: CCIAdminCF::LockServer
  157. //
  158. // Synopsis: Force class factory to remain loaded
  159. //
  160. // Arguments: [fLock] -- TRUE if locking, FALSE if unlocking
  161. //
  162. // Returns: S_OK
  163. //
  164. // History: 23-Feb-1994 KyleP Created
  165. // History: 26-Nov-1996 KyleP Created
  166. //
  167. //--------------------------------------------------------------------------
  168. SCODE STDMETHODCALLTYPE CCIAdminCF::LockServer(BOOL fLock)
  169. {
  170. if(fLock)
  171. InterlockedIncrement( &gulcInstances );
  172. else
  173. InterlockedDecrement( &gulcInstances );
  174. return S_OK;
  175. }
  176. //+-------------------------------------------------------------------------
  177. //
  178. // Function: DllGetClassObject
  179. //
  180. // Synopsis: Ole DLL load class routine
  181. //
  182. // Arguments: [cid] -- Class to load
  183. // [iid] -- Interface to bind to on class object
  184. // [ppvObj] -- Interface pointer returned here
  185. //
  186. // Returns: Text filter class factory
  187. //
  188. // History: 23-Feb-1994 KyleP Created
  189. // History: 26-Nov-1996 KyleP Created
  190. //
  191. //--------------------------------------------------------------------------
  192. extern "C" SCODE STDMETHODCALLTYPE DllGetClassObject( REFCLSID cid,
  193. REFIID iid,
  194. void ** ppvObj )
  195. {
  196. IUnknown * pResult = 0;
  197. SCODE sc = S_OK;
  198. TRANSLATE_EXCEPTIONS;
  199. TRY
  200. {
  201. if ( guidCISnapin == cid )
  202. pResult = (IUnknown *)new CCIAdminCF;
  203. else
  204. sc = E_NOINTERFACE;
  205. if( pResult )
  206. {
  207. sc = pResult->QueryInterface( iid, ppvObj );
  208. pResult->Release(); // Release extra refcount from QueryInterface
  209. }
  210. }
  211. CATCH(CException, e)
  212. {
  213. if ( pResult )
  214. pResult->Release();
  215. switch( e.GetErrorCode() )
  216. {
  217. case E_OUTOFMEMORY:
  218. sc = (E_OUTOFMEMORY);
  219. break;
  220. default:
  221. sc = (E_UNEXPECTED);
  222. }
  223. }
  224. END_CATCH;
  225. UNTRANSLATE_EXCEPTIONS;
  226. return sc;
  227. }
  228. //+-------------------------------------------------------------------------
  229. //
  230. // Method: DllCanUnloadNow
  231. //
  232. // Synopsis: Notifies DLL to unload (cleanup global resources)
  233. //
  234. // Returns: S_OK if it is acceptable for caller to unload DLL.
  235. //
  236. // History: 23-Feb-1994 KyleP Created
  237. // History: 26-Nov-1996 KyleP Created
  238. //
  239. //--------------------------------------------------------------------------
  240. extern "C" SCODE STDMETHODCALLTYPE DllCanUnloadNow( void )
  241. {
  242. if ( 0 == gulcInstances )
  243. return( S_OK );
  244. else
  245. return( S_FALSE );
  246. }