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.

1008 lines
29 KiB

  1. /**********************************************************************/
  2. /** Microsoft Windows/NT **/
  3. /** Copyright(c) Microsoft Corporation, 1997 - 1999 **/
  4. /**********************************************************************/
  5. /*
  6. ipsmcomp.cpp
  7. This file contains the derived implementations from CComponent
  8. and CComponentData for the wlanmon snapin.
  9. FILE HISTORY:
  10. */
  11. #include "stdafx.h"
  12. #include "root.h"
  13. #include "server.h"
  14. #include <atlimpl.cpp>
  15. #ifdef _DEBUG
  16. #define new DEBUG_NEW
  17. #undef THIS_FILE
  18. static char THIS_FILE[] = __FILE__;
  19. #endif
  20. DWORD gdwIpsmSnapVersion;
  21. UINT aColumns[IPSECMON_NODETYPE_MAX][MAX_COLUMNS] =
  22. {
  23. {IDS_ROOT_NAME, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0},
  24. {IDS_SERVER_NAME, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0},
  25. {0,0,0,0,0,0,0,0,0,0,0,0,0,0}, //IPFWMON_FILTER
  26. {0,0,0,0,0,0,0,0,0,0,0,0,0,0}, //IPFWMON_LOG
  27. // Wireless Log
  28. {IDS_COL_LOGDATA_COMP_ID, IDS_COL_LOGDATA_CAT, IDS_COL_LOGDATA_TIME,
  29. IDS_COL_LOGDATA_LOCAL_MAC_ADDR, IDS_COL_LOGDATA_REMOTE_MAC_ADDR,
  30. IDS_COL_LOGDATA_SSID, IDS_COL_LOGDATA_MSG, 0, 0, 0, 0, 0, 0, 0},
  31. // Access Point Data
  32. {IDS_COL_APDATA_SSID, IDS_COL_APDATA_INF_MODE, IDS_COL_APDATA_MAC,
  33. IDS_COL_APDATA_PRIVACY, IDS_COL_APDATA_RSSI, IDS_COL_APDATA_CHANNEL,
  34. IDS_COL_APDATA_RATE, IDS_COL_APDATA_GUID, 0, 0, 0, 0, 0},
  35. {0,0,0,0,0,0,0,0,0,0,0,0,0,0}
  36. };
  37. //
  38. // CODEWORK this should be in a resource, for example code on loading data resources see
  39. // D:\nt\private\net\ui\common\src\applib\applib\lbcolw.cxx ReloadColumnWidths()
  40. // JonN 10/11/96
  41. //
  42. int aColumnWidths[IPSECMON_NODETYPE_MAX][MAX_COLUMNS] =
  43. {
  44. {200, AUTO_WIDTH, AUTO_WIDTH, AUTO_WIDTH, AUTO_WIDTH, AUTO_WIDTH,
  45. AUTO_WIDTH, AUTO_WIDTH, AUTO_WIDTH, AUTO_WIDTH, AUTO_WIDTH, AUTO_WIDTH,
  46. AUTO_WIDTH, AUTO_WIDTH}, // IPSMSNAP_ROOT
  47. {200, AUTO_WIDTH, AUTO_WIDTH, AUTO_WIDTH, AUTO_WIDTH, AUTO_WIDTH,
  48. AUTO_WIDTH, AUTO_WIDTH, AUTO_WIDTH, AUTO_WIDTH, AUTO_WIDTH, AUTO_WIDTH,
  49. AUTO_WIDTH, AUTO_WIDTH}, // IPSMSNAP_SERVER
  50. {AUTO_WIDTH, AUTO_WIDTH, AUTO_WIDTH, AUTO_WIDTH, AUTO_WIDTH, AUTO_WIDTH,
  51. AUTO_WIDTH, AUTO_WIDTH, AUTO_WIDTH, AUTO_WIDTH, AUTO_WIDTH, AUTO_WIDTH,
  52. AUTO_WIDTH, AUTO_WIDTH}, // IPSECMON_LOG
  53. {AUTO_WIDTH, AUTO_WIDTH, AUTO_WIDTH, AUTO_WIDTH, AUTO_WIDTH, AUTO_WIDTH,
  54. AUTO_WIDTH, AUTO_WIDTH, AUTO_WIDTH, AUTO_WIDTH, AUTO_WIDTH, AUTO_WIDTH,
  55. AUTO_WIDTH, AUTO_WIDTH}, // IPSECMON_MAIN_MODE
  56. // Wireless Log
  57. {90, 90, 150, 125, 125, 80, 350, AUTO_WIDTH, AUTO_WIDTH, AUTO_WIDTH,
  58. AUTO_WIDTH, AUTO_WIDTH, AUTO_WIDTH, AUTO_WIDTH},
  59. // Access Point
  60. {150, 150, 150, 150, AUTO_WIDTH, AUTO_WIDTH, 150, 250,
  61. AUTO_WIDTH, AUTO_WIDTH, AUTO_WIDTH, AUTO_WIDTH, AUTO_WIDTH, AUTO_WIDTH},
  62. {AUTO_WIDTH, AUTO_WIDTH, AUTO_WIDTH, AUTO_WIDTH, AUTO_WIDTH, AUTO_WIDTH,
  63. AUTO_WIDTH, AUTO_WIDTH, AUTO_WIDTH, AUTO_WIDTH, AUTO_WIDTH, AUTO_WIDTH,
  64. AUTO_WIDTH, AUTO_WIDTH}
  65. };
  66. #define HI HIDDEN
  67. #define EN ENABLED
  68. MMC_CONSOLE_VERB g_ConsoleVerbs[] =
  69. {
  70. MMC_VERB_OPEN,
  71. MMC_VERB_COPY,
  72. MMC_VERB_PASTE,
  73. MMC_VERB_DELETE,
  74. MMC_VERB_PROPERTIES,
  75. MMC_VERB_RENAME,
  76. MMC_VERB_REFRESH,
  77. MMC_VERB_PRINT
  78. };
  79. // default states for the console verbs
  80. MMC_BUTTON_STATE g_ConsoleVerbStates[IPSECMON_NODETYPE_MAX][ARRAYLEN(g_ConsoleVerbs)] =
  81. {
  82. {HI, HI, HI, HI, HI, HI, HI, HI}, // IPSMSNAP_ROOT
  83. {HI, HI, HI, HI, HI, HI, HI, HI}, // IPSMSNAP_SERVER
  84. {HI, HI, HI, HI, HI, HI, EN, HI}, // IPSECMON_FILTER
  85. {HI, HI, HI, HI, HI, HI, HI, HI}, // IPSECMON_LOG,
  86. {HI, HI, HI, EN, HI, HI, EN, HI}, // IPFWMON_LOGDATA
  87. {HI, HI, HI, HI, HI, HI, EN, HI}, // WLANMON_APDATA
  88. {HI, HI, HI, HI, HI, HI, EN, HI}, // WLANMON_APDATA_ITEM
  89. {HI, HI, HI, HI, EN, HI, EN, HI} // IPFWMON_LOGDATA_ITEM
  90. };
  91. // default states for the console verbs
  92. MMC_BUTTON_STATE g_ConsoleVerbStatesMultiSel[IPSECMON_NODETYPE_MAX][ARRAYLEN(g_ConsoleVerbs)] =
  93. {
  94. {HI, HI, HI, HI, HI, HI, HI, HI}, // IPSMSNAP_ROOT
  95. {HI, HI, HI, HI, HI, HI, HI, HI}, // IPSMSNAP_SERVER
  96. {HI, HI, HI, HI, HI, HI, EN, HI}, // IPSECMON_FILTER
  97. {HI, HI, HI, HI, HI, HI, HI, HI}, // IPSECMON_LOG,
  98. {HI, HI, HI, EN, HI, HI, EN, HI}, // IPFWMON_LOGDATA
  99. {HI, HI, HI, HI, HI, HI, EN, HI}, // WLANMON_APDATA
  100. {HI, HI, HI, HI, HI, HI, EN, HI}, // WLANMON_APDATA_ITEM
  101. {HI, HI, HI, HI, EN, HI, EN, HI} // IPFWMON_LOGDATA_ITEM
  102. };
  103. //TODO
  104. // Help ID array for help on scope items
  105. DWORD g_dwMMCHelp[IPSECMON_NODETYPE_MAX] =
  106. {
  107. IPSMSNAP_HELP_ROOT, // IPSMSNAP_ROOT
  108. IPSMSNAP_HELP_SERVER, // IPSMSNAP_SERVER
  109. IPSMSNAP_HELP_PROVIDER, // IPSECMON_QM_SA
  110. IPSMSNAP_HELP_ROOT, // IPSECMON_FILTAER
  111. IPSMSNAP_HELP_DEVICE, // IPSECMON_QM_SA_ITEM
  112. };
  113. // icon defines
  114. UINT g_uIconMap[ICON_IDX_MAX + 1][2] =
  115. {
  116. {IDI_ICON01, ICON_IDX_SERVER},
  117. {IDI_ICON02, ICON_IDX_SERVER_BUSY},
  118. {IDI_ICON03, ICON_IDX_SERVER_CONNECTED},
  119. {IDI_ICON04, ICON_IDX_SERVER_LOST_CONNECTION},
  120. {IDI_ICON05, ICON_IDX_MACHINE},
  121. {IDI_ICON06, ICON_IDX_FOLDER_CLOSED},
  122. {IDI_ICON07, ICON_IDX_FOLDER_OPEN},
  123. {IDI_WLANMON_SNAPIN, ICON_IDX_PRODUCT},
  124. {IDI_IPSM_FILTER, ICON_IDX_FILTER},
  125. {IDI_IPSM_POLICY, ICON_IDX_POLICY},
  126. {IDI_LOG_ERROR, ICON_IDX_LOGDATA_ERROR},
  127. {IDI_LOG_WARNING, ICON_IDX_LOGDATA_WARNING},
  128. {IDI_LOG_INFO, ICON_IDX_LOGDATA_INFORMATION},
  129. {IDI_LOG_UNKNOWN, ICON_IDX_LOGDATA_UNKNOWN},
  130. {IDI_AP_ADHOC, ICON_IDX_AP_ADHOC},
  131. {IDI_AP_INFRA, ICON_IDX_AP_INFRA},
  132. {IDI_AP_ASSOC_ADHOC, ICON_IDX_AP_ASSOC_ADHOC},
  133. {IDI_AP_ASSOC_INFRA, ICON_IDX_AP_ASSOC_INFRA},
  134. {0, 0}
  135. };
  136. /*!--------------------------------------------------------------------------
  137. GetSystemMessage
  138. Use FormatMessage() to get a system error message
  139. Author: EricDav
  140. ---------------------------------------------------------------------------*/
  141. LONG
  142. GetSystemMessage
  143. (
  144. UINT nId,
  145. TCHAR * chBuffer,
  146. int cbBuffSize
  147. )
  148. {
  149. TCHAR * pszText = NULL ;
  150. HINSTANCE hdll = NULL ;
  151. DWORD flags = FORMAT_MESSAGE_IGNORE_INSERTS
  152. | FORMAT_MESSAGE_MAX_WIDTH_MASK;
  153. //
  154. // Interpret the error. Need to special case
  155. // the lmerr & ntstatus ranges, as well as
  156. // dhcp server error messages.
  157. //
  158. if( nId >= NERR_BASE && nId <= MAX_NERR )
  159. {
  160. hdll = LoadLibrary( _T("netmsg.dll") );
  161. }
  162. else if( nId >= 0x40000000L )
  163. {
  164. hdll = LoadLibrary( _T("ntdll.dll") );
  165. }
  166. if( hdll == NULL )
  167. {
  168. flags |= FORMAT_MESSAGE_FROM_SYSTEM;
  169. }
  170. else
  171. {
  172. flags |= FORMAT_MESSAGE_FROM_HMODULE;
  173. }
  174. //
  175. // Let FormatMessage do the dirty work.
  176. //
  177. DWORD dwResult = ::FormatMessage( flags,
  178. (LPVOID) hdll,
  179. nId,
  180. 0,
  181. chBuffer,
  182. cbBuffSize,
  183. NULL ) ;
  184. if( hdll != NULL )
  185. {
  186. LONG err = GetLastError();
  187. FreeLibrary( hdll );
  188. if ( dwResult == 0 )
  189. {
  190. ::SetLastError( err );
  191. }
  192. }
  193. return dwResult ? 0 : ::GetLastError() ;
  194. }
  195. /*!--------------------------------------------------------------------------
  196. LoadMessage
  197. Loads the error message from the correct DLL.
  198. Author: EricDav
  199. ---------------------------------------------------------------------------*/
  200. BOOL
  201. LoadMessage
  202. (
  203. UINT nIdPrompt,
  204. TCHAR * chMsg,
  205. int nMsgSize
  206. )
  207. {
  208. BOOL bOk;
  209. //
  210. // Substitute a friendly message for "RPC server not
  211. // available" and "No more endpoints available from
  212. // the endpoint mapper".
  213. //
  214. if (nIdPrompt == RPC_S_UNKNOWN_IF)
  215. {
  216. nIdPrompt = IDS_ERR_SPD_DOWN;
  217. }
  218. else if (nIdPrompt == RPC_S_SERVER_UNAVAILABLE)
  219. {
  220. nIdPrompt = IDS_ERR_SPD_UNAVAILABLE;
  221. }
  222. //
  223. // If it's a socket error or our error, the text is in our resource fork.
  224. // Otherwise, use FormatMessage() and the appropriate DLL.
  225. //
  226. if (nIdPrompt >= IDS_ERR_BASE && nIdPrompt < IDS_MESG_MAX)
  227. {
  228. //
  229. // It's in our resource fork
  230. //
  231. bOk = ::LoadString( AfxGetInstanceHandle(), nIdPrompt, chMsg, nMsgSize ) != 0 ;
  232. }
  233. else
  234. {
  235. //
  236. // It's in the system somewhere.
  237. //
  238. bOk = GetSystemMessage( nIdPrompt, chMsg, nMsgSize ) == 0 ;
  239. }
  240. //
  241. // If the error message did not compute, replace it.
  242. //
  243. if ( ! bOk )
  244. {
  245. TCHAR chBuff [STRING_LENGTH_MAX] ;
  246. static const TCHAR * pszReplacement = _T("System Error: %ld");
  247. const TCHAR * pszMsg = pszReplacement ;
  248. //
  249. // Try to load the generic (translatable) error message text
  250. //
  251. if ( ::LoadString( AfxGetInstanceHandle(), IDS_ERR_MESSAGE_GENERIC,
  252. chBuff, DimensionOf(chBuff) ) != 0 )
  253. {
  254. pszMsg = chBuff ;
  255. }
  256. ::wsprintf( chMsg, pszMsg, nIdPrompt ) ;
  257. }
  258. return bOk;
  259. }
  260. /*!--------------------------------------------------------------------------
  261. IpsmMessageBox
  262. Puts up a message box with the corresponding error text.
  263. Author: EricDav
  264. ---------------------------------------------------------------------------*/
  265. int
  266. IpsmMessageBox
  267. (
  268. UINT nIdPrompt,
  269. UINT nType,
  270. const TCHAR * pszSuffixString,
  271. UINT nHelpContext
  272. )
  273. {
  274. TCHAR chMesg [4000] = {0};
  275. BOOL bOk ;
  276. bOk = LoadMessage(nIdPrompt, chMesg, sizeof(chMesg)/sizeof(chMesg[0]));
  277. if ( pszSuffixString )
  278. {
  279. ::lstrcat( chMesg, _T(" ") ) ;
  280. ::lstrcat( chMesg, pszSuffixString ) ;
  281. }
  282. return ::AfxMessageBox( chMesg, nType, nHelpContext ) ;
  283. }
  284. /*!--------------------------------------------------------------------------
  285. IpsmMessageBoxEx
  286. Puts up a message box with the corresponding error text.
  287. Author: EricDav
  288. ---------------------------------------------------------------------------*/
  289. int
  290. IpsmMessageBoxEx
  291. (
  292. UINT nIdPrompt,
  293. LPCTSTR pszPrefixMessage,
  294. UINT nType,
  295. UINT nHelpContext
  296. )
  297. {
  298. AFX_MANAGE_STATE(AfxGetStaticModuleState());
  299. TCHAR chMesg[4000] = {0};
  300. CString strMessage;
  301. BOOL bOk;
  302. bOk = LoadMessage(nIdPrompt, chMesg, sizeof(chMesg)/sizeof(chMesg[0]));
  303. if ( pszPrefixMessage )
  304. {
  305. strMessage = pszPrefixMessage;
  306. strMessage += _T("\n");
  307. strMessage += _T("\n");
  308. strMessage += chMesg;
  309. }
  310. else
  311. {
  312. strMessage = chMesg;
  313. }
  314. return AfxMessageBox(strMessage, nType, nHelpContext);
  315. }
  316. /*---------------------------------------------------------------------------
  317. Class CIpsmComponent implementation
  318. ---------------------------------------------------------------------------*/
  319. CIpsmComponent::CIpsmComponent()
  320. {
  321. m_pbmpToolbar = NULL;
  322. }
  323. CIpsmComponent::~CIpsmComponent()
  324. {
  325. if (m_pbmpToolbar)
  326. {
  327. delete m_pbmpToolbar;
  328. m_pbmpToolbar = NULL;
  329. }
  330. }
  331. STDMETHODIMP CIpsmComponent::InitializeBitmaps(MMC_COOKIE cookie)
  332. {
  333. AFX_MANAGE_STATE(AfxGetStaticModuleState());
  334. ASSERT(m_spImageList != NULL);
  335. HICON hIcon;
  336. for (int i = 0; i < ICON_IDX_MAX; i++)
  337. {
  338. hIcon = LoadIcon(AfxGetInstanceHandle(), MAKEINTRESOURCE(g_uIconMap[i][0]));
  339. if (hIcon)
  340. {
  341. // call mmc
  342. VERIFY(SUCCEEDED(m_spImageList->ImageListSetIcon(reinterpret_cast<LONG_PTR*>(hIcon), g_uIconMap[i][1])));
  343. }
  344. }
  345. return S_OK;
  346. }
  347. /*!--------------------------------------------------------------------------
  348. CIpsmComponent::QueryDataObject
  349. Implementation of IComponent::QueryDataObject. We need this for
  350. virtual listbox support. MMC calls us back normally with the cookie
  351. we handed it... In the case of the VLB, it hands us the index of
  352. the item. So, we need to do some extra checking...
  353. Author: EricDav
  354. ---------------------------------------------------------------------------*/
  355. STDMETHODIMP
  356. CIpsmComponent::QueryDataObject
  357. (
  358. MMC_COOKIE cookie,
  359. DATA_OBJECT_TYPES type,
  360. LPDATAOBJECT* ppDataObject
  361. )
  362. {
  363. AFX_MANAGE_STATE(AfxGetStaticModuleState());
  364. HRESULT hr = hrOK;
  365. SPITFSNode spSelectedNode;
  366. SPITFSResultHandler spResultHandler;
  367. long lViewOptions;
  368. LPOLESTR pViewType;
  369. CDataObject * pDataObject;
  370. COM_PROTECT_TRY
  371. {
  372. // check to see what kind of result view type the selected node has
  373. CORg (GetSelectedNode(&spSelectedNode));
  374. CORg (spSelectedNode->GetResultHandler(&spResultHandler));
  375. CORg (spResultHandler->OnGetResultViewType(this, spSelectedNode->GetData(TFS_DATA_COOKIE), &pViewType, &lViewOptions));
  376. if ( (lViewOptions & MMC_VIEW_OPTIONS_OWNERDATALIST) ||
  377. (cookie == MMC_MULTI_SELECT_COOKIE) )
  378. {
  379. if (cookie == MMC_MULTI_SELECT_COOKIE)
  380. {
  381. // this is a special case for multiple select. We need to build a list
  382. // of GUIDs and the code to do this is in the handler...
  383. spResultHandler->OnCreateDataObject(this, cookie, type, ppDataObject);
  384. }
  385. else
  386. {
  387. // this node has a virtual listbox for the result pane. Gerenate
  388. // a special data object using the selected node as the cookie
  389. Assert(m_spComponentData != NULL);
  390. CORg (m_spComponentData->QueryDataObject(reinterpret_cast<MMC_COOKIE>((ITFSNode *) spSelectedNode), type, ppDataObject));
  391. }
  392. pDataObject = reinterpret_cast<CDataObject *>(*ppDataObject);
  393. pDataObject->SetVirtualIndex((int) cookie);
  394. }
  395. else
  396. {
  397. // just forward this to the component data
  398. Assert(m_spComponentData != NULL);
  399. CORg (m_spComponentData->QueryDataObject(cookie, type, ppDataObject));
  400. }
  401. COM_PROTECT_ERROR_LABEL;
  402. }
  403. COM_PROTECT_CATCH
  404. return hr;
  405. }
  406. /*!--------------------------------------------------------------------------
  407. CIpsmComponent::CompareObjects
  408. Implementation of IComponent::CompareObjects
  409. MMC calls this to compare two objects
  410. We override this for the virtual listbox case. With a virtual listbox,
  411. the cookies are the same, but the index in the internal structs
  412. indicate which item the dataobject refers to. So, we need to look
  413. at the indicies instead of just the cookies.
  414. Author:
  415. ---------------------------------------------------------------------------*/
  416. STDMETHODIMP
  417. CIpsmComponent::CompareObjects
  418. (
  419. LPDATAOBJECT lpDataObjectA,
  420. LPDATAOBJECT lpDataObjectB
  421. )
  422. {
  423. AFX_MANAGE_STATE(AfxGetStaticModuleState());
  424. if (lpDataObjectA == NULL || lpDataObjectB == NULL)
  425. return E_POINTER;
  426. // Make sure both data object are mine
  427. SPINTERNAL spA;
  428. SPINTERNAL spB;
  429. HRESULT hr = S_FALSE;
  430. COM_PROTECT_TRY
  431. {
  432. spA = ExtractInternalFormat(lpDataObjectA);
  433. spB = ExtractInternalFormat(lpDataObjectB);
  434. if (spA != NULL && spB != NULL)
  435. {
  436. if (spA->m_cookie != spB->m_cookie)
  437. {
  438. hr = S_FALSE;
  439. }
  440. else
  441. {
  442. if (spA->HasVirtualIndex() && spB->HasVirtualIndex())
  443. {
  444. hr = (spA->GetVirtualIndex() == spB->GetVirtualIndex()) ? S_OK : S_FALSE;
  445. }
  446. else
  447. {
  448. hr = S_OK;
  449. }
  450. }
  451. }
  452. }
  453. COM_PROTECT_CATCH
  454. return hr;
  455. }
  456. /*!--------------------------------------------------------------------------
  457. CIpsmComponentData::SetControlbar
  458. -
  459. Author: EricDav, KennT
  460. ---------------------------------------------------------------------------*/
  461. HRESULT
  462. CIpsmComponent::SetControlbar
  463. (
  464. LPCONTROLBAR pControlbar
  465. )
  466. {
  467. AFX_MANAGE_STATE(AfxGetStaticModuleState());
  468. HRESULT hr = hrOK;
  469. if (pControlbar)
  470. {
  471. }
  472. // store the control bar away for future use
  473. m_spControlbar.Set(pControlbar);
  474. return hr;
  475. }
  476. /*!--------------------------------------------------------------------------
  477. CIpsmComponentData::ControlbarNotify
  478. -
  479. Author: EricDav
  480. ---------------------------------------------------------------------------*/
  481. STDMETHODIMP
  482. CIpsmComponent::ControlbarNotify
  483. (
  484. MMC_NOTIFY_TYPE event,
  485. LPARAM arg,
  486. LPARAM param
  487. )
  488. {
  489. AFX_MANAGE_STATE(AfxGetStaticModuleState());
  490. HRESULT hr = hrOK;
  491. return hr;
  492. }
  493. /*!--------------------------------------------------------------------------
  494. CIpsmComponentData::OnSnapinHelp
  495. -
  496. Author: EricDav
  497. ---------------------------------------------------------------------------*/
  498. STDMETHODIMP
  499. CIpsmComponent::OnSnapinHelp
  500. (
  501. LPDATAOBJECT pDataObject,
  502. LPARAM arg,
  503. LPARAM param
  504. )
  505. {
  506. AFX_MANAGE_STATE(AfxGetStaticModuleState());
  507. HRESULT hr = hrOK;
  508. //help info here
  509. HtmlHelpA(NULL, "infrared.chm", HH_DISPLAY_TOPIC, 0);
  510. return hr;
  511. }
  512. /*---------------------------------------------------------------------------
  513. Class CIpsmComponentData implementation
  514. ---------------------------------------------------------------------------*/
  515. CIpsmComponentData::CIpsmComponentData()
  516. {
  517. gdwIpsmSnapVersion = IPSMSNAP_VERSION;
  518. }
  519. /*!--------------------------------------------------------------------------
  520. CIpsmComponentData::OnInitialize
  521. -
  522. Author: EricDav, KennT
  523. ---------------------------------------------------------------------------*/
  524. STDMETHODIMP CIpsmComponentData::OnInitialize(LPIMAGELIST pScopeImage)
  525. {
  526. AFX_MANAGE_STATE(AfxGetStaticModuleState());
  527. HICON hIcon;
  528. for (int i = 0; i < ICON_IDX_MAX; i++)
  529. {
  530. hIcon = LoadIcon(AfxGetInstanceHandle(), MAKEINTRESOURCE(g_uIconMap[i][0]));
  531. if (hIcon)
  532. {
  533. // call mmc
  534. VERIFY(SUCCEEDED(pScopeImage->ImageListSetIcon(reinterpret_cast<LONG_PTR*>(hIcon), g_uIconMap[i][1])));
  535. }
  536. }
  537. return hrOK;
  538. }
  539. /*!--------------------------------------------------------------------------
  540. CIpsmComponentData::OnDestroy
  541. -
  542. Author: EricDav, KennT
  543. ---------------------------------------------------------------------------*/
  544. STDMETHODIMP CIpsmComponentData::OnDestroy()
  545. {
  546. m_spNodeMgr.Release();
  547. return hrOK;
  548. }
  549. /*!--------------------------------------------------------------------------
  550. CIpsmComponentData::OnInitializeNodeMgr
  551. -
  552. Author: KennT
  553. ---------------------------------------------------------------------------*/
  554. STDMETHODIMP
  555. CIpsmComponentData::OnInitializeNodeMgr
  556. (
  557. ITFSComponentData * pTFSCompData,
  558. ITFSNodeMgr * pNodeMgr
  559. )
  560. {
  561. AFX_MANAGE_STATE(AfxGetStaticModuleState());
  562. // For now create a new node handler for each new node,
  563. // this is rather bogus as it can get expensive. We can
  564. // consider creating only a single node handler for each
  565. // node type.
  566. CIpsmRootHandler * pHandler = NULL;
  567. SPITFSNodeHandler spHandler;
  568. SPITFSNode spNode;
  569. HRESULT hr = hrOK;
  570. try
  571. {
  572. pHandler = new CIpsmRootHandler(pTFSCompData);
  573. // Do this so that it will get released correctly
  574. spHandler = pHandler;
  575. }
  576. catch(...)
  577. {
  578. hr = E_OUTOFMEMORY;
  579. }
  580. CORg( hr );
  581. // Create the root node for this sick puppy
  582. CORg( CreateContainerTFSNode(&spNode,
  583. &GUID_IpsmRootNodeType,
  584. pHandler,
  585. pHandler, /* result handler */
  586. pNodeMgr) );
  587. // Need to initialize the data for the root node
  588. pHandler->InitializeNode(spNode);
  589. CORg( pNodeMgr->SetRootNode(spNode) );
  590. m_spRootNode.Set(spNode);
  591. //Add help
  592. pTFSCompData->SetHTMLHelpFileName(_T("IRsnap.chm"));
  593. Error:
  594. return hr;
  595. }
  596. /*!--------------------------------------------------------------------------
  597. CIpsmComponentData::OnCreateComponent
  598. -
  599. Author: EricDav, KennT
  600. ---------------------------------------------------------------------------*/
  601. STDMETHODIMP
  602. CIpsmComponentData::OnCreateComponent
  603. (
  604. LPCOMPONENT *ppComponent
  605. )
  606. {
  607. AFX_MANAGE_STATE(AfxGetStaticModuleState());
  608. ASSERT(ppComponent != NULL);
  609. HRESULT hr = hrOK;
  610. CIpsmComponent * pComp = NULL;
  611. try
  612. {
  613. pComp = new CIpsmComponent;
  614. pComp->Construct(m_spNodeMgr,
  615. static_cast<IComponentData *>(this),
  616. m_spTFSComponentData);
  617. *ppComponent = static_cast<IComponent *>(pComp);
  618. }
  619. catch(...)
  620. {
  621. hr = E_OUTOFMEMORY;
  622. }
  623. return hr;
  624. }
  625. /*!--------------------------------------------------------------------------
  626. CIpsmComponentData::GetCoClassID
  627. -
  628. Author: KennT
  629. ---------------------------------------------------------------------------*/
  630. STDMETHODIMP_(const CLSID *)
  631. CIpsmComponentData::GetCoClassID()
  632. {
  633. return &CLSID_IpsmSnapin;
  634. }
  635. /*!--------------------------------------------------------------------------
  636. CIpsmComponentData::OnCreateDataObject
  637. -
  638. Author: KennT
  639. ---------------------------------------------------------------------------*/
  640. STDMETHODIMP
  641. CIpsmComponentData::OnCreateDataObject
  642. (
  643. MMC_COOKIE cookie,
  644. DATA_OBJECT_TYPES type,
  645. IDataObject ** ppDataObject
  646. )
  647. {
  648. AFX_MANAGE_STATE(AfxGetStaticModuleState());
  649. Assert(ppDataObject != NULL);
  650. CDataObject * pObject = NULL;
  651. SPIDataObject spDataObject;
  652. pObject = new CDataObject;
  653. spDataObject = pObject; // do this so that it gets released correctly
  654. Assert(pObject != NULL);
  655. // Save cookie and type for delayed rendering
  656. pObject->SetType(type);
  657. pObject->SetCookie(cookie);
  658. // Store the coclass with the data object
  659. pObject->SetClsid(*GetCoClassID());
  660. pObject->SetTFSComponentData(m_spTFSComponentData);
  661. return pObject->QueryInterface(IID_IDataObject,
  662. reinterpret_cast<void**>(ppDataObject));
  663. }
  664. ///////////////////////////////////////////////////////////////////////////////
  665. //// IPersistStream interface members
  666. STDMETHODIMP
  667. CIpsmComponentData::GetClassID
  668. (
  669. CLSID *pClassID
  670. )
  671. {
  672. ASSERT(pClassID != NULL);
  673. // Copy the CLSID for this snapin
  674. *pClassID = CLSID_IpsmSnapin;
  675. return hrOK;
  676. }
  677. STDMETHODIMP
  678. CIpsmComponentData::IsDirty()
  679. {
  680. HRESULT hr = hrFalse;
  681. if (m_spRootNode->GetData(TFS_DATA_DIRTY))
  682. {
  683. hr = hrOK;
  684. }
  685. return hr;
  686. }
  687. STDMETHODIMP
  688. CIpsmComponentData::Load
  689. (
  690. IStream *pStm
  691. )
  692. {
  693. HRESULT hr = hrOK;
  694. DWORD dwSavedVersion;
  695. CString str;
  696. int i, j;
  697. ASSERT(pStm);
  698. CStringArray strArrayName;
  699. CDWordArray dwArrayRefreshInterval;
  700. CDWordArray dwArrayOptions;
  701. CDWordArray dwArrayColumnInfo;
  702. ASSERT(pStm);
  703. CIpsmRootHandler * pRootHandler = GETHANDLER(CIpsmRootHandler, m_spRootNode);
  704. // set the mode for this stream
  705. XferStream xferStream(pStm, XferStream::MODE_READ);
  706. // read the version of the file format
  707. DWORD dwFileVersion;
  708. CORg(xferStream.XferDWORD(IPSMSTRM_TAG_VERSION, &dwFileVersion));
  709. if (dwFileVersion < IPSMSNAP_FILE_VERSION)
  710. {
  711. AFX_MANAGE_STATE(AfxGetStaticModuleState());
  712. AfxMessageBox(IDS_ERR_OLD_CONSOLE_FILE);
  713. return hr;
  714. }
  715. // Read the version # of the admin tool
  716. CORg(xferStream.XferDWORD(IPSMSTRM_TAG_VERSIONADMIN, &dwSavedVersion));
  717. if (dwSavedVersion < gdwIpsmSnapVersion)
  718. {
  719. // File is an older version. Warn the user and then don't
  720. // load anything else
  721. Assert(FALSE);
  722. }
  723. // now read all of the server information
  724. CORg(xferStream.XferCStringArray(IPSMSTRM_TAG_SERVER_NAME, &strArrayName));
  725. CORg(xferStream.XferDWORDArray(IPSMSTRM_TAG_SERVER_REFRESH_INTERVAL, &dwArrayRefreshInterval));
  726. CORg(xferStream.XferDWORDArray(IPSMSTRM_TAG_SERVER_OPTIONS, &dwArrayOptions));
  727. // now load the column information
  728. for (i = 0; i < NUM_SCOPE_ITEMS; i++)
  729. {
  730. CORg(xferStream.XferDWORDArray(IPSMSTRM_TAG_COLUMN_INFO, &dwArrayColumnInfo));
  731. for (j = 0; j < MAX_COLUMNS; j++)
  732. {
  733. aColumnWidths[i][j] = dwArrayColumnInfo[j];
  734. }
  735. }
  736. // now create the servers based on the information
  737. for (i = 0; i < strArrayName.GetSize(); i++)
  738. {
  739. //
  740. // now create the server object
  741. //
  742. pRootHandler->AddServer(NULL,
  743. strArrayName[i],
  744. FALSE,
  745. dwArrayOptions[i],
  746. dwArrayRefreshInterval[i],
  747. FALSE,
  748. 0,
  749. 0);
  750. }
  751. Error:
  752. return SUCCEEDED(hr) ? S_OK : E_FAIL;
  753. }
  754. STDMETHODIMP
  755. CIpsmComponentData::Save
  756. (
  757. IStream *pStm,
  758. BOOL fClearDirty
  759. )
  760. {
  761. HRESULT hr = hrOK;
  762. CStringArray strArrayName;
  763. CDWordArray dwArrayRefreshInterval;
  764. CDWordArray dwArrayOptions;
  765. CDWordArray dwArrayColumnInfo;
  766. ASSERT(pStm);
  767. // set the mode for this stream
  768. XferStream xferStream(pStm, XferStream::MODE_WRITE);
  769. CString str;
  770. // Write the version # of the file format
  771. DWORD dwFileVersion = IPSMSNAP_FILE_VERSION;
  772. xferStream.XferDWORD(IPSMSTRM_TAG_VERSION, &dwFileVersion);
  773. // Write the version # of the admin tool
  774. xferStream.XferDWORD(IPSMSTRM_TAG_VERSIONADMIN, &gdwIpsmSnapVersion);
  775. //
  776. // Build our array of servers
  777. //
  778. int nNumServers = 0, nVisibleCount = 0;
  779. hr = m_spRootNode->GetChildCount(&nVisibleCount, &nNumServers);
  780. strArrayName.SetSize(nNumServers);
  781. dwArrayRefreshInterval.SetSize(nNumServers);
  782. dwArrayOptions.SetSize(nNumServers);
  783. dwArrayColumnInfo.SetSize(MAX_COLUMNS);
  784. //
  785. // loop and save off all the server's attributes
  786. //
  787. SPITFSNodeEnum spNodeEnum;
  788. SPITFSNode spCurrentNode;
  789. ULONG nNumReturned = 0;
  790. int nCount = 0;
  791. m_spRootNode->GetEnum(&spNodeEnum);
  792. spNodeEnum->Next(1, &spCurrentNode, &nNumReturned);
  793. while (nNumReturned)
  794. {
  795. CIpsmServer * pServer = GETHANDLER(CIpsmServer, spCurrentNode);
  796. // query the server for it's options:
  797. // auto refresh
  798. dwArrayRefreshInterval[nCount] = pServer->GetAutoRefreshInterval();
  799. dwArrayOptions[nCount] = pServer->GetOptions();
  800. // put the information in our array
  801. strArrayName[nCount] = pServer->GetName();
  802. // go to the next node
  803. spCurrentNode.Release();
  804. spNodeEnum->Next(1, &spCurrentNode, &nNumReturned);
  805. nCount++;
  806. }
  807. // now write out all of the server information
  808. xferStream.XferCStringArray(IPSMSTRM_TAG_SERVER_NAME, &strArrayName);
  809. xferStream.XferDWORDArray(IPSMSTRM_TAG_SERVER_REFRESH_INTERVAL, &dwArrayRefreshInterval);
  810. xferStream.XferDWORDArray(IPSMSTRM_TAG_SERVER_OPTIONS, &dwArrayOptions);
  811. // now save the column information
  812. for (int i = 0; i < NUM_SCOPE_ITEMS; i++)
  813. {
  814. for (int j = 0; j < MAX_COLUMNS; j++)
  815. {
  816. dwArrayColumnInfo[j] = aColumnWidths[i][j];
  817. }
  818. xferStream.XferDWORDArray(IPSMSTRM_TAG_COLUMN_INFO, &dwArrayColumnInfo);
  819. }
  820. if (fClearDirty)
  821. {
  822. m_spRootNode->SetData(TFS_DATA_DIRTY, FALSE);
  823. }
  824. return SUCCEEDED(hr) ? S_OK : STG_E_CANTSAVE;
  825. }
  826. STDMETHODIMP
  827. CIpsmComponentData::GetSizeMax
  828. (
  829. ULARGE_INTEGER *pcbSize
  830. )
  831. {
  832. ASSERT(pcbSize);
  833. // Set the size of the string to be saved
  834. ULISet32(*pcbSize, 10000);
  835. return S_OK;
  836. }
  837. STDMETHODIMP
  838. CIpsmComponentData::InitNew()
  839. {
  840. return hrOK;
  841. }
  842. HRESULT
  843. CIpsmComponentData::FinalConstruct()
  844. {
  845. HRESULT hr = hrOK;
  846. hr = CComponentData::FinalConstruct();
  847. if (FHrSucceeded(hr))
  848. {
  849. m_spTFSComponentData->GetNodeMgr(&m_spNodeMgr);
  850. }
  851. return hr;
  852. }
  853. void
  854. CIpsmComponentData::FinalRelease()
  855. {
  856. CComponentData::FinalRelease();
  857. }