//+------------------------------------------------------------------------- // // Microsoft Windows // // Copyright (C) Microsoft Corporation, 1997 - 1999 // // File: chooser.cpp // //-------------------------------------------------------------------------- ///////////////////////////////////////////////////////////////////// // Chooser.cpp // // Dialog to choose a machine name. // // PURPOSE // What you have to do is to copy all the files from the // snapin\chooser\ directory into your project (you may add // \nt\private\admin\snapin\chooser\ to your include directory if // you prefer not copying the code). // If you decide to copy the code to your project, please send mail // to Dan Morin (T-DanM) and cc to Jon Newman (JonN) so we can // mail you when we have updates available. The next update will // be the "Browse" button to select a machine name. // // // DYNALOADED LIBRARIES // // HISTORY // 13-May-1997 t-danm Creation. // 23-May-1997 t-danm Checkin into public tree. Comments updates. // 25-May-1997 t-danm Added MMCPropPageCallback(). // 31-Oct-1997 mattt Added dynaload, fixed user logic // 1-Oct-1998 mattt Removed reliance on MFC, changed default look to enable certsvr picker // ///////////////////////////////////////////////////////////////////// #include #include "chooser.h" #include "csdisp.h" // certsrv picker #ifdef _DEBUG #undef THIS_FILE #define THIS_FILE __FILE__ #endif #ifndef INOUT // The following defines are found in \nt\private\admin\snapin\filemgmt\stdafx.h #define INOUT #define Endorse(f) // Dummy macro #define LENGTH(x) (sizeof(x)/sizeof(x[0])) #define Assert(f) ASSERT(f) #endif ///////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////// // Replacement for BEGIN_MESSAGE_MAP BOOL CAutoDeletePropPage::OnCommand(WPARAM wParam, LPARAM lParam) { /* switch(LOWORD(wParam)) { } */ return FALSE; } ///////////////////////////////////////////////////////////////////// // Constructor CAutoDeletePropPage::CAutoDeletePropPage(UINT uIDD) : PropertyPage(uIDD) { m_prgzHelpIDs = NULL; m_autodeleteStuff.cWizPages = 1; // Number of pages in wizard m_autodeleteStuff.pfnOriginalPropSheetPageProc = m_psp.pfnCallback; m_psp.dwFlags |= PSP_USECALLBACK; m_psp.pfnCallback = S_PropSheetPageProc; m_psp.lParam = reinterpret_cast(this); } CAutoDeletePropPage::~CAutoDeletePropPage() { } ///////////////////////////////////////////////////////////////////// void CAutoDeletePropPage::SetCaption(LPCTSTR pszCaption) { m_strCaption = pszCaption; // Copy the caption m_psp.pszTitle = m_strCaption; // Set the title m_psp.dwFlags |= PSP_USETITLE; } ///////////////////////////////////////////////////////////////////// void CAutoDeletePropPage::SetCaption(UINT uStringID) { VERIFY(m_strCaption.LoadString(uStringID)); SetCaption(m_strCaption); } ///////////////////////////////////////////////////////////////////// void CAutoDeletePropPage::SetHelp(LPCTSTR szHelpFile, const DWORD rgzHelpIDs[]) { m_strHelpFile = szHelpFile; m_prgzHelpIDs = rgzHelpIDs; } ///////////////////////////////////////////////////////////////////// void CAutoDeletePropPage::EnableDlgItem(INT nIdDlgItem, BOOL fEnable) { Assert(IsWindow(::GetDlgItem(m_hWnd, nIdDlgItem))); ::EnableWindow(::GetDlgItem(m_hWnd, nIdDlgItem), fEnable); } ///////////////////////////////////////////////////////////////////// BOOL CAutoDeletePropPage::OnSetActive() { HWND hwndParent = ::GetParent(m_hWnd); Assert(IsWindow(hwndParent)); ::PropSheet_SetWizButtons(hwndParent, PSWIZB_FINISH); return PropertyPage::OnSetActive(); } ///////////////////////////////////////////////////////////////////// void CAutoDeletePropPage::OnHelp(LPHELPINFO pHelpInfo) { if (m_prgzHelpIDs == NULL || m_strHelpFile.IsEmpty()) return; if (pHelpInfo != NULL && pHelpInfo->iContextType == HELPINFO_WINDOW) { // Display context help for a control ::WinHelp((HWND)pHelpInfo->hItemHandle, m_strHelpFile, HELP_WM_HELP, (ULONG_PTR)(LPVOID)m_prgzHelpIDs); } return; } ///////////////////////////////////////////////////////////////////// void CAutoDeletePropPage::OnContextHelp(HWND hwnd) { if (m_prgzHelpIDs == NULL || m_strHelpFile.IsEmpty()) return; Assert(IsWindow(hwnd)); ::WinHelp(hwnd, m_strHelpFile, HELP_CONTEXTMENU, (ULONG_PTR)(LPVOID)m_prgzHelpIDs); return; } ///////////////////////////////////////////////////////////////////// // S_PropSheetPageProc() // // Static member function used to delete the CAutoDeletePropPage object // when wizard terminates // UINT CALLBACK CAutoDeletePropPage::S_PropSheetPageProc( HWND hwnd, UINT uMsg, LPPROPSHEETPAGE ppsp) { Assert(ppsp != NULL); CAutoDeletePropPage * pThis; pThis = reinterpret_cast(ppsp->lParam); Assert(pThis != NULL); BOOL fDefaultRet; switch (uMsg) { case PSPCB_RELEASE: fDefaultRet = FALSE; if (--(pThis->m_autodeleteStuff.cWizPages) <= 0) { // Remember callback on stack since "this" will be deleted LPFNPSPCALLBACK pfnOrig = pThis->m_autodeleteStuff.pfnOriginalPropSheetPageProc; delete pThis; if (pfnOrig) return (pfnOrig)(hwnd, uMsg, ppsp); else return fDefaultRet; } break; case PSPCB_CREATE: fDefaultRet = TRUE; // do not increase refcount, PSPCB_CREATE may or may not be called // depending on whether the page was created. PSPCB_RELEASE can be // depended upon to be called exactly once per page however. break; } // switch if (pThis->m_autodeleteStuff.pfnOriginalPropSheetPageProc) return (pThis->m_autodeleteStuff.pfnOriginalPropSheetPageProc)(hwnd, uMsg, ppsp); else return fDefaultRet; } // CAutoDeletePropPage::S_PropSheetPageProc() ///////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////// // Replacement for BEGIN_MESSAGE_MAP BOOL CChooseMachinePropPage::OnCommand(WPARAM wParam, LPARAM lParam) { switch(LOWORD(wParam)) { case IDC_CHOOSER_RADIO_LOCAL_MACHINE: OnRadioLocalMachine(); break; case IDC_CHOOSER_RADIO_SPECIFIC_MACHINE: OnRadioSpecificMachine(); break; case IDC_CHOOSER_BUTTON_BROWSE_MACHINENAMES: OnBrowse(); break; default: return FALSE; break; } return TRUE; } #ifdef _DEBUG static void AssertValidDialogTemplate(HWND hwnd) { ASSERT(::IsWindow(hwnd)); // Mandatory controls for a valid dialog template static const UINT rgzidDialogControl[] = { IDC_CHOOSER_RADIO_LOCAL_MACHINE, IDC_CHOOSER_RADIO_SPECIFIC_MACHINE, IDC_CHOOSER_EDIT_MACHINE_NAME, 0 }; for (int i = 0; rgzidDialogControl[i] != 0; i++) { ASSERT(NULL != GetDlgItem(hwnd, rgzidDialogControl[i]) && "Control ID not found in dialog template."); } } // AssertValidDialogTemplate() #else #define AssertValidDialogTemplate(hwnd) #endif // ~_DEBUG ///////////////////////////////////////////////////////////////////// // Constructor CChooseMachinePropPage::CChooseMachinePropPage(UINT uIDD) : CAutoDeletePropPage(uIDD) { m_fIsRadioLocalMachine = TRUE; m_fEnableMachineBrowse = FALSE; m_pstrMachineNameOut = NULL; m_pstrMachineNameEffectiveOut = NULL; m_pdwFlags = NULL; } ///////////////////////////////////////////////////////////////////// CChooseMachinePropPage::~CChooseMachinePropPage() { } ///////////////////////////////////////////////////////////////////// // Load the initial state of CChooseMachinePropPage void CChooseMachinePropPage::InitMachineName(LPCTSTR pszMachineName) { m_strMachineName = pszMachineName; m_fIsRadioLocalMachine = m_strMachineName.IsEmpty(); } ///////////////////////////////////////////////////////////////////// // SetOutputBuffers() // // - Set the pointer to the CString object to store the machine name. // - Set the pointer to the boolean flag for command line override. // - Set the pointer pointer to store the overriden machine name. // void CChooseMachinePropPage::SetOutputBuffers( OUT CString * pstrMachineNamePersist, // Machine name the user typed. Empty string == local machine. OUT CString * pstrMachineNameEffective, OUT DWORD* pdwFlags) { Assert(pstrMachineNamePersist != NULL && "Invalid output buffer"); // point members at params m_pstrMachineNameOut = pstrMachineNamePersist; m_pstrMachineNameEffectiveOut = pstrMachineNameEffective; m_pdwFlags = pdwFlags; *m_pdwFlags = 0; } ///////////////////////////////////////////////////////////////////// // Replacement for DoDataExchange BOOL CChooseMachinePropPage::UpdateData(BOOL fSuckFromDlg /*= TRUE*/) { if (fSuckFromDlg) { m_strMachineName.FromWindow(GetDlgItem(m_hWnd, IDC_CHOOSER_EDIT_MACHINE_NAME)); int iCheck = (int)SendMessage(GetDlgItem(m_hWnd, IDC_CHOOSER_MACHINE_OVERRIDE), BM_GETCHECK, 0, 0); if (iCheck == BST_CHECKED) *m_pdwFlags |= CCOMPDATAIMPL_FLAGS_ALLOW_MACHINE_OVERRIDE; else *m_pdwFlags &= ~CCOMPDATAIMPL_FLAGS_ALLOW_MACHINE_OVERRIDE; } else { m_strMachineName.ToWindow(GetDlgItem(m_hWnd, IDC_CHOOSER_EDIT_MACHINE_NAME)); int iCheck; iCheck = (*m_pdwFlags & CCOMPDATAIMPL_FLAGS_ALLOW_MACHINE_OVERRIDE) ? BST_CHECKED : BST_UNCHECKED; SendMessage(GetDlgItem(m_hWnd, IDC_CHOOSER_MACHINE_OVERRIDE), BM_SETCHECK, iCheck, 0); } return TRUE; } ///////////////////////////////////////////////////////////////////// BOOL CChooseMachinePropPage::OnInitDialog() { AssertValidDialogTemplate(m_hWnd); CAutoDeletePropPage::OnInitDialog(); InitChooserControls(); PropSheet_SetWizButtons(GetParent(), PSWIZB_FINISH); return TRUE; } ///////////////////////////////////////////////////////////////////// BOOL CChooseMachinePropPage::OnWizardFinish() { if (!UpdateData()) // Do the data exchange to collect data return FALSE; // don't destroy on error if (m_fIsRadioLocalMachine) m_strMachineName.Empty(); else if (m_strMachineName.IsEmpty()) { DisplayCertSrvErrorWithContext(m_hWnd, S_OK, IDS_MUST_CHOOSE_MACHINE); return FALSE; } if (m_pstrMachineNameOut != NULL) { // Store the machine name into its output buffer *m_pstrMachineNameOut = m_strMachineName; if (m_pstrMachineNameEffectiveOut != NULL) { *m_pstrMachineNameEffectiveOut = m_strMachineName; } // if } else Assert(FALSE && "FYI: You have not specified any output buffer to store the machine name."); return CAutoDeletePropPage::OnWizardFinish(); } void CChooseMachinePropPage::InitChooserControls() { SendDlgItemMessage(IDC_CHOOSER_RADIO_LOCAL_MACHINE, BM_SETCHECK, m_fIsRadioLocalMachine); SendDlgItemMessage(IDC_CHOOSER_RADIO_SPECIFIC_MACHINE, BM_SETCHECK, !m_fIsRadioLocalMachine); EnableDlgItem(IDC_CHOOSER_EDIT_MACHINE_NAME, !m_fIsRadioLocalMachine); PCCRYPTUI_CA_CONTEXT pCAContext = NULL; DWORD dwCACount; HRESULT hr = myGetConfigFromPicker( m_hWnd, NULL, //sub title NULL, //title NULL, TRUE, //use ds TRUE, // count only &dwCACount, &pCAContext); if (S_OK != hr && HRESULT_FROM_WIN32(ERROR_CANCELLED) != hr) { _PrintError(hr, "myGetConfigFromPicker"); goto done; } m_fEnableMachineBrowse = (0 == dwCACount) ? FALSE : TRUE; if (NULL != pCAContext) { CryptUIDlgFreeCAContext(pCAContext); } done: EnableDlgItem(IDC_CHOOSER_BUTTON_BROWSE_MACHINENAMES, !m_fIsRadioLocalMachine && m_fEnableMachineBrowse); } void CChooseMachinePropPage::OnRadioLocalMachine() { m_fIsRadioLocalMachine = TRUE; EnableDlgItem(IDC_CHOOSER_EDIT_MACHINE_NAME, FALSE); EnableDlgItem(IDC_CHOOSER_BUTTON_BROWSE_MACHINENAMES, FALSE); } void CChooseMachinePropPage::OnRadioSpecificMachine() { m_fIsRadioLocalMachine = FALSE; EnableDlgItem(IDC_CHOOSER_EDIT_MACHINE_NAME, TRUE); EnableDlgItem(IDC_CHOOSER_BUTTON_BROWSE_MACHINENAMES, m_fEnableMachineBrowse); } void CChooseMachinePropPage::OnBrowse() { HRESULT hr; WCHAR *szConfig = NULL; CWaitCursor cwait; // UNDONE: expand config picker to non-published (DS chooser dlg) hr = myGetConfigStringFromPicker(m_hWnd, NULL, //use default prompt NULL, //use default title NULL, //use default shared folder TRUE, //use DS &szConfig); if (hr == S_OK) { LPWSTR szWhack = wcschr(szConfig, L'\\'); if (szWhack != NULL) szWhack[0] = L'\0'; m_strMachineName = szConfig; LocalFree(szConfig); } // push result back to ui UpdateData(FALSE); }