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.

1301 lines
26 KiB

  1. /*++
  2. Copyright (c) 1994-2000 Microsoft Corporation
  3. Module Name :
  4. FtpAddNew.cpp
  5. Abstract:
  6. Implementation for classes used in creation of new FTP site and virtual directory
  7. Author:
  8. Sergei Antonov (sergeia)
  9. Project:
  10. Internet Services Manager
  11. Revision History:
  12. 11/8/2000 sergeia Initial creation
  13. --*/
  14. #include "stdafx.h"
  15. #include "common.h"
  16. #include "strfn.h"
  17. #include "inetprop.h"
  18. #include "InetMgrApp.h"
  19. #include "iisobj.h"
  20. #include "ftpsht.h"
  21. #include "wizard.h"
  22. #include "FtpAddNew.h"
  23. #ifdef _DEBUG
  24. #undef THIS_FILE
  25. static char BASED_CODE THIS_FILE[] = __FILE__;
  26. #endif
  27. #define new DEBUG_NEW
  28. #define DEF_PORT (21)
  29. #define MAX_ALIAS_NAME (240) // Ref Bug 241148
  30. HRESULT
  31. RebindInterface(OUT IN CMetaInterface * pInterface,
  32. OUT BOOL * pfContinue, IN DWORD dwCancelError);
  33. extern CComModule _Module;
  34. HRESULT
  35. CIISMBNode::AddFTPSite(
  36. const CSnapInObjectRootBase * pObj,
  37. DATA_OBJECT_TYPES type,
  38. DWORD * inst
  39. )
  40. {
  41. CFtpWizSettings ws(
  42. dynamic_cast<CMetaKey *>(QueryInterface()),
  43. QueryMachineName(),
  44. TRUE
  45. );
  46. CIISWizardSheet sheet(
  47. IDB_WIZ_FTP_LEFT, IDB_WIZ_FTP_HEAD);
  48. CIISWizardBookEnd pgWelcome(
  49. IDS_FTP_NEW_SITE_WELCOME,
  50. IDS_FTP_NEW_SITE_WIZARD,
  51. IDS_FTP_NEW_SITE_BODY
  52. );
  53. CFtpWizDescription pgDescr(&ws);
  54. CFtpWizBindings pgBindings(&ws);
  55. CFtpWizPath pgHome(&ws, FALSE);
  56. CFtpWizUserName pgUserName(&ws, FALSE);
  57. CFtpWizPermissions pgPerms(&ws, FALSE);
  58. CIISWizardBookEnd pgCompletion(
  59. &ws.m_hrResult,
  60. IDS_FTP_NEW_SITE_SUCCESS,
  61. IDS_FTP_NEW_SITE_FAILURE,
  62. IDS_FTP_NEW_SITE_WIZARD
  63. );
  64. sheet.AddPage(&pgWelcome);
  65. sheet.AddPage(&pgDescr);
  66. sheet.AddPage(&pgBindings);
  67. sheet.AddPage(&pgHome);
  68. sheet.AddPage(&pgUserName);
  69. sheet.AddPage(&pgPerms);
  70. sheet.AddPage(&pgCompletion);
  71. if (sheet.DoModal() == IDCANCEL)
  72. {
  73. return CError::HResult(ERROR_CANCELLED);
  74. }
  75. if (inst != NULL && SUCCEEDED(ws.m_hrResult))
  76. {
  77. *inst = ws.m_dwInstance;
  78. }
  79. return ws.m_hrResult;
  80. }
  81. HRESULT
  82. CIISMBNode::AddFTPVDir(
  83. const CSnapInObjectRootBase * pObj,
  84. DATA_OBJECT_TYPES type,
  85. CString& alias
  86. )
  87. {
  88. CFtpWizSettings ws(
  89. dynamic_cast<CMetaKey *>(QueryInterface()),
  90. QueryMachineName(),
  91. FALSE
  92. );
  93. CComBSTR path;
  94. BuildMetaPath(path);
  95. ws.m_strParent = path;
  96. CIISWizardSheet sheet(
  97. IDB_WIZ_FTP_LEFT, IDB_WIZ_FTP_HEAD);
  98. CIISWizardBookEnd pgWelcome(
  99. IDS_FTP_NEW_VDIR_WELCOME,
  100. IDS_FTP_NEW_VDIR_WIZARD,
  101. IDS_FTP_NEW_VDIR_BODY
  102. );
  103. CFtpWizAlias pgAlias(&ws);
  104. CFtpWizPath pgHome(&ws, TRUE);
  105. CFtpWizUserName pgUserName(&ws, TRUE);
  106. CFtpWizPermissions pgPerms(&ws, TRUE);
  107. CIISWizardBookEnd pgCompletion(
  108. &ws.m_hrResult,
  109. IDS_FTP_NEW_VDIR_SUCCESS,
  110. IDS_FTP_NEW_VDIR_FAILURE,
  111. IDS_FTP_NEW_VDIR_WIZARD
  112. );
  113. sheet.AddPage(&pgWelcome);
  114. sheet.AddPage(&pgAlias);
  115. sheet.AddPage(&pgHome);
  116. sheet.AddPage(&pgUserName);
  117. sheet.AddPage(&pgPerms);
  118. sheet.AddPage(&pgCompletion);
  119. if (sheet.DoModal() == IDCANCEL)
  120. {
  121. return CError::HResult(ERROR_CANCELLED);
  122. }
  123. if (SUCCEEDED(ws.m_hrResult))
  124. {
  125. alias = ws.m_strAlias;
  126. }
  127. return ws.m_hrResult;
  128. }
  129. CFtpWizSettings::CFtpWizSettings(
  130. CMetaKey * pMetaKey,
  131. LPCTSTR lpszServerName,
  132. BOOL fNewSite,
  133. DWORD dwInstance,
  134. LPCTSTR lpszParent
  135. ) :
  136. m_hrResult(S_OK),
  137. m_pKey(pMetaKey),
  138. m_fNewSite(fNewSite),
  139. m_fUNC(FALSE),
  140. m_fRead(FALSE),
  141. m_fWrite(FALSE),
  142. m_dwInstance(dwInstance)
  143. {
  144. ASSERT(lpszServerName != NULL);
  145. m_strServerName = lpszServerName;
  146. m_fLocal = IsServerLocal(m_strServerName);
  147. if (lpszParent)
  148. {
  149. m_strParent = lpszParent;
  150. }
  151. }
  152. IMPLEMENT_DYNCREATE(CFtpWizDescription, CIISWizardPage)
  153. CFtpWizDescription::CFtpWizDescription(CFtpWizSettings * pData)
  154. : CIISWizardPage(
  155. CFtpWizDescription::IDD, IDS_FTP_NEW_SITE_WIZARD, HEADER_PAGE
  156. ),
  157. m_pSettings(pData)
  158. {
  159. }
  160. CFtpWizDescription::~CFtpWizDescription()
  161. {
  162. }
  163. //
  164. // Message Map
  165. //
  166. BEGIN_MESSAGE_MAP(CFtpWizDescription, CIISWizardPage)
  167. //{{AFX_MSG_MAP(CFtpWizDescription)
  168. ON_EN_CHANGE(IDC_EDIT_DESCRIPTION, OnChangeEditDescription)
  169. //}}AFX_MSG_MAP
  170. END_MESSAGE_MAP()
  171. void
  172. CFtpWizDescription::OnChangeEditDescription()
  173. {
  174. SetControlStates();
  175. }
  176. LRESULT
  177. CFtpWizDescription::OnWizardNext()
  178. {
  179. if (!ValidateString(m_edit_Description,
  180. m_pSettings->m_strDescription, 1, MAX_PATH))
  181. {
  182. return -1;
  183. }
  184. return CIISWizardPage::OnWizardNext();
  185. }
  186. BOOL
  187. CFtpWizDescription::OnSetActive()
  188. {
  189. SetControlStates();
  190. return CIISWizardPage::OnSetActive();
  191. }
  192. void
  193. CFtpWizDescription::DoDataExchange(CDataExchange * pDX)
  194. {
  195. CIISWizardPage::DoDataExchange(pDX);
  196. //{{AFX_DATA_MAP(CFtpWizDescription)
  197. DDX_Control(pDX, IDC_EDIT_DESCRIPTION, m_edit_Description);
  198. //}}AFX_DATA_MAP
  199. }
  200. void
  201. CFtpWizDescription::SetControlStates()
  202. {
  203. DWORD dwFlags = PSWIZB_BACK;
  204. if (m_edit_Description.GetWindowTextLength() > 0)
  205. {
  206. dwFlags |= PSWIZB_NEXT;
  207. }
  208. SetWizardButtons(dwFlags);
  209. }
  210. ///////////////////////////////////////////
  211. //
  212. // New Virtual Directory Wizard Alias Page
  213. //
  214. // <<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<
  215. IMPLEMENT_DYNCREATE(CFtpWizAlias, CIISWizardPage)
  216. CFtpWizAlias::CFtpWizAlias(
  217. IN OUT CFtpWizSettings * pSettings
  218. )
  219. /*++
  220. Routine Description:
  221. Constructor
  222. Arguments:
  223. CString & strServerName : Server name
  224. Return Value:
  225. None
  226. --*/
  227. : CIISWizardPage(
  228. CFtpWizAlias::IDD,
  229. IDS_FTP_NEW_VDIR_WIZARD,
  230. HEADER_PAGE
  231. ),
  232. m_pSettings(pSettings)
  233. //m_strAlias()
  234. {
  235. #if 0 // Keep Class Wizard Happy
  236. //{{AFX_DATA_INIT(CFtpWizAlias)
  237. m_strAlias = _T("");
  238. //}}AFX_DATA_INIT
  239. #endif // 0
  240. }
  241. CFtpWizAlias::~CFtpWizAlias()
  242. /*++
  243. Routine Description:
  244. Destructor
  245. Arguments:
  246. N/A
  247. Return Value:
  248. N/A
  249. --*/
  250. {
  251. }
  252. void
  253. CFtpWizAlias::DoDataExchange(
  254. IN CDataExchange * pDX
  255. )
  256. /*++
  257. Routine Description:
  258. Initialise/Store control data
  259. Arguments:
  260. CDataExchange * pDX - DDX/DDV control structure
  261. Return Value:
  262. None
  263. --*/
  264. {
  265. CIISWizardPage::DoDataExchange(pDX);
  266. //{{AFX_DATA_MAP(CFtpWizAlias)
  267. DDX_Control(pDX, IDC_EDIT_ALIAS, m_edit_Alias);
  268. //}}AFX_DATA_MAP
  269. }
  270. LRESULT
  271. CFtpWizAlias::OnWizardNext()
  272. /*++
  273. Routine Description:
  274. prevent the / and \ characters from being in the alias name
  275. Arguments:
  276. None
  277. Return Value:
  278. None
  279. --*/
  280. {
  281. if (!ValidateString(
  282. m_edit_Alias,
  283. m_pSettings->m_strAlias,
  284. 1,
  285. MAX_ALIAS_NAME
  286. ))
  287. {
  288. return -1;
  289. }
  290. //
  291. // Find the illegal characters. If they exist tell
  292. // the user and don't go on.
  293. //
  294. if (m_pSettings->m_strAlias.FindOneOf(_T("/\\?*")) >= 0)
  295. {
  296. AfxMessageBox(IDS_ILLEGAL_ALIAS_CHARS);
  297. m_edit_Alias.SetFocus();
  298. m_edit_Alias.SetSel(0, -1);
  299. //
  300. // prevent the wizard page from changing
  301. //
  302. return -1;
  303. }
  304. //
  305. // Allow the wizard to continue
  306. //
  307. return CIISWizardPage::OnWizardNext();
  308. }
  309. void
  310. CFtpWizAlias::SetControlStates()
  311. /*++
  312. Routine Description:
  313. Set the state of the control data
  314. Arguments:
  315. None
  316. Return Value:
  317. None
  318. --*/
  319. {
  320. DWORD dwFlags = PSWIZB_BACK;
  321. if (m_edit_Alias.GetWindowTextLength() > 0)
  322. {
  323. dwFlags |= PSWIZB_NEXT;
  324. }
  325. SetWizardButtons(dwFlags);
  326. }
  327. //
  328. // Message Map
  329. //
  330. BEGIN_MESSAGE_MAP(CFtpWizAlias, CIISWizardPage)
  331. //{{AFX_MSG_MAP(CFtpWizAlias)
  332. ON_EN_CHANGE(IDC_EDIT_ALIAS, OnChangeEditAlias)
  333. //}}AFX_MSG_MAP
  334. END_MESSAGE_MAP()
  335. //
  336. // Message Handlers
  337. //
  338. // <<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<
  339. BOOL
  340. CFtpWizAlias::OnSetActive()
  341. /*++
  342. Routine Description:
  343. Activation handler
  344. Arguments:
  345. None
  346. Return Value:
  347. TRUE for success, FALSE for failure
  348. --*/
  349. {
  350. SetControlStates();
  351. return CIISWizardPage::OnSetActive();
  352. }
  353. void
  354. CFtpWizAlias::OnChangeEditAlias()
  355. /*++
  356. Routine Description:
  357. 'edit change' handler
  358. Arguments:
  359. None
  360. Return Value:
  361. None
  362. --*/
  363. {
  364. SetControlStates();
  365. }
  366. ///////////////////////////////////////////
  367. IMPLEMENT_DYNCREATE(CFtpWizBindings, CIISWizardPage)
  368. CFtpWizBindings::CFtpWizBindings(
  369. IN OUT CFtpWizSettings * pSettings
  370. )
  371. : CIISWizardPage(CFtpWizBindings::IDD,
  372. IDS_FTP_NEW_SITE_WIZARD, HEADER_PAGE
  373. ),
  374. m_pSettings(pSettings),
  375. m_iaIpAddress(),
  376. m_oblIpAddresses()
  377. {
  378. //{{AFX_DATA_INIT(CFtpWizBindings)
  379. m_nTCPPort = DEF_PORT;
  380. m_nIpAddressSel = -1;
  381. //}}AFX_DATA_INIT
  382. }
  383. CFtpWizBindings::~CFtpWizBindings()
  384. {
  385. }
  386. void
  387. CFtpWizBindings::DoDataExchange(
  388. IN CDataExchange * pDX
  389. )
  390. {
  391. CIISWizardPage::DoDataExchange(pDX);
  392. //{{AFX_DATA_MAP(CFtpWizBindings)
  393. DDX_Control(pDX, IDC_COMBO_IP_ADDRESSES, m_combo_IpAddresses);
  394. DDX_Text(pDX, IDC_EDIT_TCP_PORT, m_nTCPPort);
  395. DDV_MinMaxUInt(pDX, m_nTCPPort, 1, 65535);
  396. //}}AFX_DATA_MAP
  397. DDX_CBIndex(pDX, IDC_COMBO_IP_ADDRESSES, m_nIpAddressSel);
  398. if (pDX->m_bSaveAndValidate)
  399. {
  400. if (!FetchIpAddressFromCombo(
  401. m_combo_IpAddresses,
  402. m_oblIpAddresses,
  403. m_iaIpAddress
  404. ))
  405. {
  406. pDX->Fail();
  407. }
  408. CString strDomain;
  409. CInstanceProps::BuildBinding(
  410. m_pSettings->m_strBinding,
  411. m_iaIpAddress,
  412. m_nTCPPort,
  413. strDomain
  414. );
  415. }
  416. }
  417. void
  418. CFtpWizBindings::SetControlStates()
  419. {
  420. SetWizardButtons(PSWIZB_NEXT | PSWIZB_BACK);
  421. }
  422. //
  423. // Message Map
  424. //
  425. BEGIN_MESSAGE_MAP(CFtpWizBindings, CIISWizardPage)
  426. //{{AFX_MSG_MAP(CFtpWizBindings)
  427. //}}AFX_MSG_MAP
  428. END_MESSAGE_MAP()
  429. //
  430. // Message Handlers
  431. //
  432. // <<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<
  433. BOOL
  434. CFtpWizBindings::OnInitDialog()
  435. {
  436. CIISWizardPage::OnInitDialog();
  437. BeginWaitCursor();
  438. PopulateComboWithKnownIpAddresses(
  439. m_pSettings->m_strServerName,
  440. m_combo_IpAddresses,
  441. m_iaIpAddress,
  442. m_oblIpAddresses,
  443. m_nIpAddressSel
  444. );
  445. EndWaitCursor();
  446. return TRUE;
  447. }
  448. BOOL
  449. CFtpWizBindings::OnSetActive()
  450. {
  451. SetControlStates();
  452. return CIISWizardPage::OnSetActive();
  453. }
  454. ///////////////////////////////////////////
  455. IMPLEMENT_DYNCREATE(CFtpWizPath, CIISWizardPage)
  456. CFtpWizPath::CFtpWizPath(
  457. IN OUT CFtpWizSettings * pSettings,
  458. IN BOOL bVDir
  459. )
  460. : CIISWizardPage(
  461. (bVDir ? IDD_NEW_FTP_DIR_PATH : IDD_NEW_FTP_INST_HOME), // Template
  462. (bVDir ? IDS_FTP_NEW_VDIR_WIZARD : IDS_FTP_NEW_SITE_WIZARD), // Caption
  463. HEADER_PAGE // Header page
  464. ),
  465. m_pSettings(pSettings)
  466. {
  467. #if 0 // Keep ClassWizard happy
  468. //{{AFX_DATA_INIT(CFtpWizPath)
  469. m_strPath = _T("");
  470. //}}AFX_DATA_INIT
  471. #endif // 0
  472. }
  473. CFtpWizPath::~CFtpWizPath()
  474. {
  475. }
  476. void
  477. CFtpWizPath::DoDataExchange(
  478. IN CDataExchange * pDX
  479. )
  480. {
  481. CIISWizardPage::DoDataExchange(pDX);
  482. //{{AFX_DATA_MAP(CFtpWizPath)
  483. DDX_Control(pDX, IDC_BUTTON_BROWSE, m_button_Browse);
  484. DDX_Control(pDX, IDC_EDIT_PATH, m_edit_Path);
  485. //}}AFX_DATA_MAP
  486. DDX_Text(pDX, IDC_EDIT_PATH, m_pSettings->m_strPath);
  487. DDV_MaxChars(pDX, m_pSettings->m_strPath, MAX_PATH);
  488. }
  489. void
  490. CFtpWizPath::SetControlStates()
  491. {
  492. DWORD dwFlags = PSWIZB_BACK;
  493. if (m_edit_Path.GetWindowTextLength() > 0)
  494. {
  495. dwFlags |= PSWIZB_NEXT;
  496. }
  497. SetWizardButtons(dwFlags);
  498. }
  499. //
  500. // Message Map
  501. //
  502. BEGIN_MESSAGE_MAP(CFtpWizPath, CIISWizardPage)
  503. //{{AFX_MSG_MAP(CFtpWizPath)
  504. ON_EN_CHANGE(IDC_EDIT_PATH, OnChangeEditPath)
  505. ON_BN_CLICKED(IDC_BUTTON_BROWSE, OnButtonBrowse)
  506. //}}AFX_MSG_MAP
  507. END_MESSAGE_MAP()
  508. //
  509. // Message Handlers
  510. //
  511. // <<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<
  512. BOOL
  513. CFtpWizPath::OnSetActive()
  514. {
  515. SetControlStates();
  516. return CIISWizardPage::OnSetActive();
  517. }
  518. LRESULT
  519. CFtpWizPath::OnWizardNext()
  520. {
  521. if (!ValidateString(m_edit_Path, m_pSettings->m_strPath, 1, MAX_PATH))
  522. {
  523. return -1;
  524. }
  525. if (!PathIsValid(m_pSettings->m_strPath))
  526. {
  527. m_edit_Path.SetSel(0,-1);
  528. m_edit_Path.SetFocus();
  529. ::AfxMessageBox(IDS_ERR_BAD_PATH);
  530. }
  531. m_pSettings->m_fUNC = IsUNCName(m_pSettings->m_strPath);
  532. if (!m_pSettings->m_fUNC)
  533. {
  534. if (!IsFullyQualifiedPath(m_pSettings->m_strPath)
  535. && !IsDevicePath(m_pSettings->m_strPath)
  536. )
  537. {
  538. m_edit_Path.SetSel(0,-1);
  539. m_edit_Path.SetFocus();
  540. ::AfxMessageBox(IDS_ERR_BAD_PATH);
  541. return -1;
  542. }
  543. if (m_pSettings->m_fLocal)
  544. {
  545. DWORD dwAttr = GetFileAttributes(m_pSettings->m_strPath);
  546. if (dwAttr == 0xffffffff ||
  547. (dwAttr & FILE_ATTRIBUTE_DIRECTORY) == 0)
  548. {
  549. m_edit_Path.SetSel(0,-1);
  550. m_edit_Path.SetFocus();
  551. ::AfxMessageBox(IDS_ERR_PATH_NOT_FOUND);
  552. return -1;
  553. }
  554. }
  555. }
  556. return CIISWizardPage::OnWizardNext();
  557. }
  558. void
  559. CFtpWizPath::OnChangeEditPath()
  560. {
  561. SetControlStates();
  562. }
  563. static int CALLBACK
  564. FileChooserCallback(HWND hwnd, UINT uMsg, LPARAM lParam, LPARAM lpData)
  565. {
  566. CFtpWizPath * pThis = (CFtpWizPath *)lpData;
  567. ASSERT(pThis != NULL);
  568. return pThis->BrowseForFolderCallback(hwnd, uMsg, lParam);
  569. }
  570. int
  571. CFtpWizPath::BrowseForFolderCallback(HWND hwnd, UINT uMsg, LPARAM lParam)
  572. {
  573. switch (uMsg)
  574. {
  575. case BFFM_INITIALIZED:
  576. ASSERT(m_pPathTemp != NULL);
  577. if (::PathIsNetworkPath(m_pPathTemp))
  578. return 0;
  579. while (!::PathIsDirectory(m_pPathTemp))
  580. {
  581. if (0 == ::PathRemoveFileSpec(m_pPathTemp) && !::PathIsRoot(m_pPathTemp))
  582. {
  583. return 0;
  584. }
  585. DWORD attr = GetFileAttributes(m_pPathTemp);
  586. if ((attr & FILE_ATTRIBUTE_READONLY) == 0)
  587. break;
  588. }
  589. ::SendMessage(hwnd, BFFM_SETSELECTION, TRUE, (LPARAM)m_pPathTemp);
  590. break;
  591. case BFFM_SELCHANGED:
  592. {
  593. LPITEMIDLIST pidl = (LPITEMIDLIST)lParam;
  594. TCHAR path[MAX_PATH];
  595. if (SHGetPathFromIDList(pidl, path))
  596. {
  597. ::SendMessage(hwnd, BFFM_ENABLEOK, 0, !PathIsNetworkPath(path));
  598. }
  599. }
  600. break;
  601. case BFFM_VALIDATEFAILED:
  602. break;
  603. }
  604. return 0;
  605. }
  606. void
  607. CFtpWizPath::OnButtonBrowse()
  608. {
  609. ASSERT(m_pSettings->m_fLocal);
  610. BOOL bRes = FALSE;
  611. HRESULT hr;
  612. CString str;
  613. m_edit_Path.GetWindowText(str);
  614. if (SUCCEEDED(hr = CoInitialize(NULL)))
  615. {
  616. LPITEMIDLIST pidl = NULL;
  617. if (SUCCEEDED(SHGetFolderLocation(NULL, CSIDL_DRIVES, NULL, 0, &pidl)))
  618. {
  619. LPITEMIDLIST pidList = NULL;
  620. BROWSEINFO bi;
  621. TCHAR buf[MAX_PATH];
  622. ZeroMemory(&bi, sizeof(bi));
  623. int drive = PathGetDriveNumber(str);
  624. if (GetDriveType(PathBuildRoot(buf, drive)) == DRIVE_FIXED)
  625. {
  626. StrCpy(buf, str);
  627. }
  628. else
  629. {
  630. buf[0] = 0;
  631. }
  632. m_strBrowseTitle.LoadString(m_pSettings->m_fNewSite ?
  633. IDS_FTP_NEW_SITE_WIZARD : IDS_FTP_NEW_VDIR_WIZARD);
  634. bi.hwndOwner = m_hWnd;
  635. bi.pidlRoot = pidl;
  636. bi.pszDisplayName = m_pPathTemp = buf;
  637. bi.lpszTitle = m_strBrowseTitle;
  638. bi.ulFlags |= BIF_NEWDIALOGSTYLE | BIF_RETURNONLYFSDIRS/* | BIF_EDITBOX*/;
  639. bi.lpfn = FileChooserCallback;
  640. bi.lParam = (LPARAM)this;
  641. pidList = SHBrowseForFolder(&bi);
  642. if ( pidList != NULL
  643. && SHGetPathFromIDList(pidList, buf)
  644. )
  645. {
  646. str = buf;
  647. bRes = TRUE;
  648. }
  649. IMalloc * pMalloc;
  650. VERIFY(SUCCEEDED(SHGetMalloc(&pMalloc)));
  651. if (pidl != NULL)
  652. pMalloc->Free(pidl);
  653. pMalloc->Release();
  654. }
  655. CoUninitialize();
  656. }
  657. if (bRes)
  658. {
  659. m_edit_Path.SetWindowText(str);
  660. SetControlStates();
  661. }
  662. }
  663. BOOL
  664. CFtpWizPath::OnInitDialog()
  665. {
  666. CIISWizardPage::OnInitDialog();
  667. m_button_Browse.EnableWindow(m_pSettings->m_fLocal);
  668. return TRUE;
  669. }
  670. ///////////////////////////////////////////
  671. IMPLEMENT_DYNCREATE(CFtpWizUserName, CIISWizardPage)
  672. CFtpWizUserName::CFtpWizUserName(
  673. IN OUT CFtpWizSettings * pSettings,
  674. IN BOOL bVDir
  675. )
  676. : CIISWizardPage(
  677. CFtpWizUserName::IDD,
  678. (bVDir ? IDS_FTP_NEW_VDIR_WIZARD : IDS_FTP_NEW_SITE_WIZARD),
  679. HEADER_PAGE,
  680. (bVDir ? USE_DEFAULT_CAPTION : IDS_FTP_NEW_SITE_SECURITY_TITLE),
  681. (bVDir ? USE_DEFAULT_CAPTION : IDS_FTP_NEW_SITE_SECURITY_SUBTITLE)
  682. ),
  683. m_pSettings(pSettings)
  684. {
  685. #if 0 // Keep Class Wizard Happy
  686. //{{AFX_DATA_INIT(CFtpWizUserName)
  687. //}}AFX_DATA_INIT
  688. #endif // 0
  689. }
  690. CFtpWizUserName::~CFtpWizUserName()
  691. {
  692. }
  693. void
  694. CFtpWizUserName::DoDataExchange(
  695. IN CDataExchange * pDX
  696. )
  697. {
  698. CIISWizardPage::DoDataExchange(pDX);
  699. //{{AFX_DATA_MAP(CFtpWizUserName)
  700. DDX_Control(pDX, IDC_EDIT_USERNAME, m_edit_UserName);
  701. DDX_Control(pDX, IDC_EDIT_PASSWORD, m_edit_Password);
  702. //}}AFX_DATA_MAP
  703. //
  704. // Private DDX/DDV Routines
  705. //
  706. DDX_Text(pDX, IDC_EDIT_USERNAME, m_pSettings->m_strUserName);
  707. DDV_MaxChars(pDX, m_pSettings->m_strUserName, UNLEN);
  708. //
  709. // Some people have a tendency to add "\\" before
  710. // the computer name in user accounts. Fix this here.
  711. //
  712. m_pSettings->m_strUserName.TrimLeft();
  713. while (*m_pSettings->m_strUserName == '\\')
  714. {
  715. m_pSettings->m_strUserName = m_pSettings->m_strUserName.Mid(2);
  716. }
  717. DDX_Password(pDX, IDC_EDIT_PASSWORD, m_pSettings->m_strPassword, g_lpszDummyPassword);
  718. DDV_MaxChars(pDX, m_pSettings->m_strPassword, PWLEN);
  719. }
  720. void
  721. CFtpWizUserName::SetControlStates()
  722. {
  723. DWORD dwFlags = PSWIZB_BACK;
  724. if (m_edit_UserName.GetWindowTextLength() > 0)
  725. {
  726. dwFlags |= PSWIZB_NEXT;
  727. }
  728. SetWizardButtons(dwFlags);
  729. }
  730. //
  731. // Message Map
  732. //
  733. BEGIN_MESSAGE_MAP(CFtpWizUserName, CIISWizardPage)
  734. //{{AFX_MSG_MAP(CFtpWizUserName)
  735. ON_BN_CLICKED(IDC_BUTTON_BROWSE_USERS, OnButtonBrowseUsers)
  736. ON_EN_CHANGE(IDC_EDIT_USERNAME, OnChangeEditUsername)
  737. ON_BN_CLICKED(IDC_BUTTON_CHECK_PASSWORD, OnButtonCheckPassword)
  738. //}}AFX_MSG_MAP
  739. END_MESSAGE_MAP()
  740. //
  741. // Message Handlers
  742. //
  743. // <<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<
  744. BOOL
  745. CFtpWizUserName::OnSetActive()
  746. {
  747. if (!m_pSettings->m_fUNC)
  748. {
  749. return 0;
  750. }
  751. SetControlStates();
  752. return CIISWizardPage::OnSetActive();
  753. }
  754. BOOL
  755. CFtpWizUserName::OnInitDialog()
  756. {
  757. CIISWizardPage::OnInitDialog();
  758. return TRUE;
  759. }
  760. LRESULT
  761. CFtpWizUserName::OnWizardNext()
  762. {
  763. if (!ValidateString(
  764. m_edit_UserName,
  765. m_pSettings->m_strUserName,
  766. 1,
  767. UNLEN
  768. ))
  769. {
  770. return -1;
  771. }
  772. return CIISWizardPage::OnWizardNext();
  773. }
  774. void
  775. CFtpWizUserName::OnButtonBrowseUsers()
  776. {
  777. CString str;
  778. if (GetIUsrAccount(m_pSettings->m_strServerName, this, str))
  779. {
  780. //
  781. // If a name was selected, blank
  782. // out the password
  783. //
  784. m_edit_UserName.SetWindowText(str);
  785. m_edit_Password.SetFocus();
  786. }
  787. }
  788. void
  789. CFtpWizUserName::OnChangeEditUsername()
  790. {
  791. m_edit_Password.SetWindowText(_T(""));
  792. SetControlStates();
  793. }
  794. void
  795. CFtpWizUserName::OnButtonCheckPassword()
  796. {
  797. if (!UpdateData(TRUE))
  798. {
  799. return;
  800. }
  801. CError err(CComAuthInfo::VerifyUserPassword(
  802. m_pSettings->m_strUserName,
  803. m_pSettings->m_strPassword
  804. ));
  805. if (!err.MessageBoxOnFailure())
  806. {
  807. ::AfxMessageBox(IDS_PASSWORD_OK);
  808. }
  809. }
  810. ///////////////////////////////////////////
  811. IMPLEMENT_DYNCREATE(CFtpWizPermissions, CIISWizardPage)
  812. CFtpWizPermissions::CFtpWizPermissions(
  813. IN OUT CFtpWizSettings * pSettings,
  814. IN BOOL bVDir
  815. )
  816. /*++
  817. Routine Description:
  818. Constructor
  819. Arguments:
  820. CString & strServerName : Server name
  821. BOOL bVDir : TRUE if this is a vdir page,
  822. FALSE if this is an instance page
  823. Return Value:
  824. None
  825. --*/
  826. : CIISWizardPage(
  827. IDD_FTP_NEW_PERMS,
  828. (bVDir ? IDS_FTP_NEW_VDIR_WIZARD : IDS_FTP_NEW_SITE_WIZARD),
  829. HEADER_PAGE,
  830. (bVDir ? USE_DEFAULT_CAPTION : IDS_FTP_NEW_SITE_PERMS_TITLE),
  831. (bVDir ? USE_DEFAULT_CAPTION : IDS_FTP_NEW_SITE_PERMS_SUBTITLE)
  832. ),
  833. m_bVDir(bVDir),
  834. m_pSettings(pSettings)
  835. {
  836. //{{AFX_DATA_INIT(CFtpWizPermissions)
  837. //}}AFX_DATA_INIT
  838. m_pSettings->m_fRead = TRUE;
  839. m_pSettings->m_fWrite = FALSE;
  840. }
  841. CFtpWizPermissions::~CFtpWizPermissions()
  842. {
  843. }
  844. void
  845. CFtpWizPermissions::DoDataExchange(
  846. IN CDataExchange * pDX
  847. )
  848. {
  849. CIISWizardPage::DoDataExchange(pDX);
  850. //{{AFX_DATA_MAP(CFtpWizPermissions)
  851. //}}AFX_DATA_MAP
  852. DDX_Check(pDX, IDC_CHECK_READ, m_pSettings->m_fRead);
  853. DDX_Check(pDX, IDC_CHECK_WRITE, m_pSettings->m_fWrite);
  854. }
  855. void
  856. CFtpWizPermissions::SetControlStates()
  857. {
  858. SetWizardButtons(PSWIZB_BACK | PSWIZB_NEXT);
  859. }
  860. //
  861. // Message Map
  862. //
  863. BEGIN_MESSAGE_MAP(CFtpWizPermissions, CIISWizardPage)
  864. //{{AFX_MSG_MAP(CFtpWizPermissions)
  865. //}}AFX_MSG_MAP
  866. END_MESSAGE_MAP()
  867. //
  868. // Message Handlers
  869. //
  870. // <<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<
  871. BOOL
  872. CFtpWizPermissions::OnSetActive()
  873. {
  874. SetControlStates();
  875. return CIISWizardPage::OnSetActive();
  876. }
  877. LRESULT
  878. CFtpWizPermissions::OnWizardNext()
  879. {
  880. if (!UpdateData(TRUE))
  881. {
  882. return -1;
  883. }
  884. ASSERT(m_pSettings != NULL);
  885. CWaitCursor wait;
  886. CError err;
  887. BOOL fRepeat;
  888. //
  889. // Build permissions DWORD
  890. //
  891. DWORD dwPermissions = 0L;
  892. SET_FLAG_IF(m_pSettings->m_fRead, dwPermissions, MD_ACCESS_READ);
  893. SET_FLAG_IF(m_pSettings->m_fWrite, dwPermissions, MD_ACCESS_WRITE);
  894. if (m_bVDir)
  895. {
  896. //
  897. // First see if by any chance this name already exists
  898. //
  899. CMetabasePath target(FALSE,
  900. m_pSettings->m_strParent, m_pSettings->m_strAlias);
  901. CChildNodeProps node(
  902. m_pSettings->m_pKey,
  903. target);
  904. do
  905. {
  906. fRepeat = FALSE;
  907. err = node.LoadData();
  908. if (err.Win32Error() == RPC_S_SERVER_UNAVAILABLE)
  909. {
  910. err = RebindInterface(
  911. m_pSettings->m_pKey,
  912. &fRepeat,
  913. ERROR_CANCELLED
  914. );
  915. }
  916. } while (fRepeat);
  917. if (err.Succeeded())
  918. {
  919. BOOL fNotUnique = TRUE;
  920. //
  921. // If the item existed without a VrPath, we'll just blow it
  922. // away, as a vdir takes presedence over a directory/file.
  923. //
  924. if (node.GetPath().IsEmpty())
  925. {
  926. err = CChildNodeProps::Delete(
  927. m_pSettings->m_pKey,
  928. m_pSettings->m_strParent,
  929. m_pSettings->m_strAlias
  930. );
  931. fNotUnique = !err.Succeeded();
  932. }
  933. //
  934. // This one already exists and exists as a virtual
  935. // directory, so away with it.
  936. //
  937. if (fNotUnique)
  938. {
  939. ::AfxMessageBox(IDS_ERR_ALIAS_NOT_UNIQUE);
  940. return IDD_FTP_NEW_DIR_ALIAS;
  941. }
  942. }
  943. //
  944. // Create new vdir
  945. //
  946. do
  947. {
  948. fRepeat = FALSE;
  949. err = CChildNodeProps::Add(
  950. m_pSettings->m_pKey,
  951. m_pSettings->m_strParent,
  952. m_pSettings->m_strAlias, // Desired alias name
  953. m_pSettings->m_strAlias, // Name returned here (may differ)
  954. &dwPermissions, // Permissions
  955. NULL, // dir browsing
  956. m_pSettings->m_strPath, // Physical path of this directory
  957. (m_pSettings->m_fUNC ? (LPCTSTR)m_pSettings->m_strUserName : NULL),
  958. (m_pSettings->m_fUNC ? (LPCTSTR)m_pSettings->m_strPassword : NULL),
  959. TRUE // Name must be unique
  960. );
  961. if (err.Win32Error() == RPC_S_SERVER_UNAVAILABLE)
  962. {
  963. err = RebindInterface(
  964. m_pSettings->m_pKey,
  965. &fRepeat,
  966. ERROR_CANCELLED
  967. );
  968. }
  969. } while (fRepeat);
  970. }
  971. else
  972. {
  973. //
  974. // Create new instance
  975. //
  976. do
  977. {
  978. fRepeat = FALSE;
  979. err = CFTPInstanceProps::Add(
  980. m_pSettings->m_pKey,
  981. SZ_MBN_FTP,
  982. m_pSettings->m_strPath,
  983. (m_pSettings->m_fUNC ? (LPCTSTR)m_pSettings->m_strUserName : NULL),
  984. (m_pSettings->m_fUNC ? (LPCTSTR)m_pSettings->m_strPassword : NULL),
  985. m_pSettings->m_strDescription,
  986. m_pSettings->m_strBinding,
  987. NULL,
  988. &dwPermissions,
  989. NULL,
  990. NULL,
  991. &m_pSettings->m_dwInstance
  992. );
  993. if (err.Win32Error() == RPC_S_SERVER_UNAVAILABLE)
  994. {
  995. err = RebindInterface(
  996. m_pSettings->m_pKey,
  997. &fRepeat,
  998. ERROR_CANCELLED
  999. );
  1000. }
  1001. } while (fRepeat);
  1002. }
  1003. m_pSettings->m_hrResult = err;
  1004. return CIISWizardPage::OnWizardNext();
  1005. }
  1006. HRESULT
  1007. RebindInterface(
  1008. OUT IN CMetaInterface * pInterface,
  1009. OUT BOOL * pfContinue,
  1010. IN DWORD dwCancelError
  1011. )
  1012. /*++
  1013. Routine Description:
  1014. Rebind the interface
  1015. Arguments:
  1016. CMetaInterface * pInterface : Interface to rebind
  1017. BOOL * pfContinue : Returns TRUE to continue.
  1018. DWORD dwCancelError : Return code on cancel
  1019. Return Value:
  1020. HRESULT
  1021. --*/
  1022. {
  1023. CError err;
  1024. CString str, strFmt;
  1025. ASSERT(pInterface != NULL);
  1026. ASSERT(pfContinue != NULL);
  1027. VERIFY(strFmt.LoadString(IDS_RECONNECT_WARNING));
  1028. str.Format(strFmt, (LPCTSTR)pInterface->QueryServerName());
  1029. if (*pfContinue = (YesNoMessageBox(str)))
  1030. {
  1031. //
  1032. // Attempt to rebind the handle
  1033. //
  1034. err = pInterface->Regenerate();
  1035. }
  1036. else
  1037. {
  1038. //
  1039. // Do not return an error in this case.
  1040. //
  1041. err = dwCancelError;
  1042. }
  1043. return err;
  1044. }