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.

710 lines
23 KiB

  1. /////////////////////////////////////////////////////////////////////////////////
  2. //
  3. // Microsoft Windows
  4. // Copyright (C) Microsoft Corporation, 2000-2001.
  5. //
  6. // File: TemplateV2RequestPropertyPage.cpp
  7. //
  8. // Contents: Implementation of CTemplateV2RequestPropertyPage
  9. //
  10. //----------------------------------------------------------------------------
  11. // TemplateV2RequestPropertyPage.cpp : implementation file
  12. //
  13. #include "stdafx.h"
  14. #include "TemplateV2RequestPropertyPage.h"
  15. #ifdef _DEBUG
  16. #define new DEBUG_NEW
  17. #undef THIS_FILE
  18. static char THIS_FILE[] = __FILE__;
  19. #endif
  20. /////////////////////////////////////////////////////////////////////////////
  21. // CTemplateV2RequestPropertyPage property page
  22. enum {
  23. REQUEST_PURPOSE_SIGNATURE = 0,
  24. REQUEST_PURPOSE_ENCRYPTION,
  25. REQUEST_PURPOSE_SIGNATURE_AND_ENCRYPTION
  26. };
  27. CTemplateV2RequestPropertyPage::CTemplateV2RequestPropertyPage(
  28. CCertTemplate& rCertTemplate, bool& rbIsDirty) :
  29. CHelpPropertyPage(CTemplateV2RequestPropertyPage::IDD),
  30. m_rCertTemplate (rCertTemplate),
  31. m_rbIsDirty (rbIsDirty),
  32. m_nProvDSSCnt (0)
  33. {
  34. _TRACE (1, L"Entering CTemplateV2RequestPropertyPage::CTemplateV2RequestPropertyPage ()\n");
  35. //{{AFX_DATA_INIT(CTemplateV2RequestPropertyPage)
  36. //}}AFX_DATA_INIT
  37. m_rCertTemplate.AddRef ();
  38. _TRACE (-1, L"Leaving CTemplateV2RequestPropertyPage::CTemplateV2RequestPropertyPage ()\n");
  39. }
  40. CTemplateV2RequestPropertyPage::~CTemplateV2RequestPropertyPage()
  41. {
  42. _TRACE (1, L"Entering CTemplateV2RequestPropertyPage::~CTemplateV2RequestPropertyPage ()\n");
  43. while ( !m_CSPList.IsEmpty () )
  44. {
  45. CT_CSP_DATA* pCSPData = m_CSPList.RemoveHead ();
  46. if ( pCSPData )
  47. delete pCSPData;
  48. }
  49. m_rCertTemplate.Release ();
  50. _TRACE (-1, L"Leaving CTemplateV2RequestPropertyPage::~CTemplateV2RequestPropertyPage ()\n");
  51. }
  52. void CTemplateV2RequestPropertyPage::DoDataExchange(CDataExchange* pDX)
  53. {
  54. CHelpPropertyPage::DoDataExchange(pDX);
  55. //{{AFX_DATA_MAP(CTemplateV2RequestPropertyPage)
  56. DDX_Control(pDX, IDC_MINIMUM_KEYSIZE_VALUE, m_minKeySizeCombo);
  57. DDX_Control(pDX, IDC_PURPOSE_COMBO, m_purposeCombo);
  58. DDX_Control(pDX, IDC_CSP_LIST, m_CSPListbox);
  59. //}}AFX_DATA_MAP
  60. }
  61. BEGIN_MESSAGE_MAP(CTemplateV2RequestPropertyPage, CHelpPropertyPage)
  62. //{{AFX_MSG_MAP(CTemplateV2RequestPropertyPage)
  63. ON_CBN_SELCHANGE(IDC_PURPOSE_COMBO, OnSelchangePurposeCombo)
  64. ON_BN_CLICKED(IDC_EXPORT_PRIVATE_KEY, OnExportPrivateKey)
  65. ON_BN_CLICKED(IDC_ARCHIVE_KEY_CHECK, OnArchiveKeyCheck)
  66. ON_BN_CLICKED(IDC_INCLUDE_SYMMETRIC_ALGORITHMS_CHECK, OnIncludeSymmetricAlgorithmsCheck)
  67. ON_CBN_SELCHANGE(IDC_MINIMUM_KEYSIZE_VALUE, OnSelchangeMinimumKeysizeValue)
  68. ON_BN_CLICKED(IDC_USER_INPUT_REQUIRED_FOR_AUTOENROLLMENT, OnUserInputRequiredForAutoenrollment)
  69. ON_BN_CLICKED(IDC_DELETE_PERMANENTLY, OnDeletePermanently)
  70. //}}AFX_MSG_MAP
  71. ON_CONTROL(CLBN_CHKCHANGE, IDC_CSP_LIST, OnCheckChange)
  72. END_MESSAGE_MAP()
  73. /////////////////////////////////////////////////////////////////////////////
  74. // CTemplateV2RequestPropertyPage message handlers
  75. BOOL CTemplateV2RequestPropertyPage::OnInitDialog()
  76. {
  77. _TRACE (1, L"Entering CTemplateV2RequestPropertyPage::OnInitDialog ()\n");
  78. CHelpPropertyPage::OnInitDialog();
  79. CString text;
  80. VERIFY (text.LoadString (IDS_SIGNATURE));
  81. int nIndex = m_purposeCombo.AddString (text);
  82. if ( nIndex >= 0 )
  83. {
  84. m_purposeCombo.SetItemData (nIndex, (DWORD_PTR) REQUEST_PURPOSE_SIGNATURE);
  85. if ( m_rCertTemplate.HasKeySpecSignature () )
  86. m_purposeCombo.SetCurSel (nIndex);
  87. }
  88. VERIFY (text.LoadString (IDS_ENCRYPTION));
  89. nIndex = m_purposeCombo.AddString (text);
  90. if ( nIndex >= 0 )
  91. {
  92. m_purposeCombo.SetItemData (nIndex, (DWORD_PTR) REQUEST_PURPOSE_ENCRYPTION);
  93. if ( m_rCertTemplate.HasEncryptionSignature () )
  94. m_purposeCombo.SetCurSel (nIndex);
  95. }
  96. VERIFY (text.LoadString (IDS_SIGNATURE_AND_ENCRYPTION));
  97. nIndex = m_purposeCombo.AddString (text);
  98. if ( nIndex >= 0 )
  99. {
  100. // NTRAID# 278356 CertSRV: No CSPs in mmc certificate snapin advanced
  101. // option list with v2 templates that have ENC and SIG as purpose.
  102. bool bHasDigitalSignature = false;
  103. m_rCertTemplate.GetDigitalSignature (bHasDigitalSignature);
  104. m_purposeCombo.SetItemData (nIndex, (DWORD_PTR) REQUEST_PURPOSE_SIGNATURE_AND_ENCRYPTION);
  105. if ( m_rCertTemplate.HasEncryptionSignature () &&
  106. (bHasDigitalSignature || m_rCertTemplate.HasKeySpecSignature ()) )
  107. m_purposeCombo.SetCurSel (nIndex);
  108. }
  109. // Initialize minimum key size combo box- values in powers of 2 from 512 to 16384
  110. DWORD dwMinKeySize = 0;
  111. m_rCertTemplate.GetMinimumKeySize (dwMinKeySize);
  112. AddKeySizeToCombo(512, L"512", dwMinKeySize);
  113. AddKeySizeToCombo(768, L"768", dwMinKeySize);
  114. AddKeySizeToCombo(1024, L"1024", dwMinKeySize);
  115. AddKeySizeToCombo(2048, L"2048", dwMinKeySize);
  116. AddKeySizeToCombo(4096, L"4096", dwMinKeySize);
  117. AddKeySizeToCombo(8192, L"8192", dwMinKeySize);
  118. AddKeySizeToCombo(16384, L"16384", dwMinKeySize);
  119. if ( SUCCEEDED (EnumerateCSPs (dwMinKeySize)) )
  120. {
  121. }
  122. if ( m_rCertTemplate.PrivateKeyIsExportable () )
  123. SendDlgItemMessage (IDC_EXPORT_PRIVATE_KEY, BM_SETCHECK, BST_CHECKED);
  124. if ( m_rCertTemplate.AllowPrivateKeyArchival () )
  125. SendDlgItemMessage (IDC_ARCHIVE_KEY_CHECK, BM_SETCHECK, BST_CHECKED);
  126. if ( m_rCertTemplate.IncludeSymmetricAlgorithms () )
  127. SendDlgItemMessage (IDC_INCLUDE_SYMMETRIC_ALGORITHMS_CHECK, BM_SETCHECK, BST_CHECKED);
  128. GetDlgItem (IDC_ARCHIVE_KEY_CHECK)->ShowWindow (SW_SHOW);
  129. GetDlgItem (IDC_MINIMUM_KEYSIZE_VALUE)->ShowWindow (SW_SHOW);
  130. GetDlgItem (IDC_MINIMUM_KEYSIZE_LABEL)->ShowWindow (SW_SHOW);
  131. GetDlgItem (IDC_INCLUDE_SYMMETRIC_ALGORITHMS_CHECK)->ShowWindow (SW_SHOW);
  132. if ( m_rCertTemplate.UserInteractionRequired () )
  133. SendDlgItemMessage (IDC_USER_INPUT_REQUIRED_FOR_AUTOENROLLMENT, BM_SETCHECK, BST_CHECKED);
  134. if ( m_rCertTemplate.IsMachineType () || m_rCertTemplate.SubjectIsCA () ||
  135. m_rCertTemplate.SubjectIsCrossCA () )
  136. {
  137. GetDlgItem (IDC_USER_INPUT_REQUIRED_FOR_AUTOENROLLMENT)->EnableWindow (FALSE);
  138. }
  139. if ( m_rCertTemplate.RemoveInvalidCertFromPersonalStore () )
  140. SendDlgItemMessage (IDC_DELETE_PERMANENTLY, BM_SETCHECK, BST_CHECKED);
  141. EnableControls ();
  142. _TRACE (-1, L"Leaving CTemplateV2RequestPropertyPage::OnInitDialog ()\n");
  143. return TRUE; // return TRUE unless you set the focus to a control
  144. // EXCEPTION: OCX Property Pages should return FALSE
  145. }
  146. void CTemplateV2RequestPropertyPage::EnableControls ()
  147. {
  148. if ( m_rCertTemplate.ReadOnly () )
  149. {
  150. GetDlgItem (IDC_PURPOSE_COMBO)->EnableWindow (FALSE);
  151. int nCnt = m_CSPListbox.GetCount ();
  152. for (int nIndex = 0; nIndex < nCnt; nIndex++)
  153. m_CSPListbox.Enable (nIndex, FALSE);
  154. GetDlgItem (IDC_EXPORT_PRIVATE_KEY)->EnableWindow (FALSE);
  155. //version 2 fields
  156. GetDlgItem (IDC_ARCHIVE_KEY_CHECK)->EnableWindow (FALSE);
  157. GetDlgItem (IDC_INCLUDE_SYMMETRIC_ALGORITHMS_CHECK)->EnableWindow (FALSE);
  158. SendDlgItemMessage (IDC_INCLUDE_SYMMETRIC_ALGORITHMS_CHECK, BM_SETCHECK, BST_UNCHECKED);
  159. GetDlgItem (IDC_MINIMUM_KEYSIZE_LABEL)->EnableWindow (FALSE);
  160. GetDlgItem (IDC_MINIMUM_KEYSIZE_VALUE)->EnableWindow (FALSE);
  161. GetDlgItem (IDC_USER_INPUT_REQUIRED_FOR_AUTOENROLLMENT)->EnableWindow (FALSE);
  162. GetDlgItem (IDC_DELETE_PERMANENTLY)->EnableWindow (FALSE);
  163. }
  164. else
  165. {
  166. BOOL bEncryptionSelected = FALSE;
  167. int nIndex = m_purposeCombo.GetCurSel ();
  168. if ( nIndex >= 0 )
  169. {
  170. switch (m_purposeCombo.GetItemData (nIndex))
  171. {
  172. case REQUEST_PURPOSE_SIGNATURE:
  173. bEncryptionSelected = FALSE;
  174. break;
  175. case REQUEST_PURPOSE_SIGNATURE_AND_ENCRYPTION:
  176. case REQUEST_PURPOSE_ENCRYPTION:
  177. bEncryptionSelected = TRUE;
  178. break;
  179. default:
  180. _ASSERT (0);
  181. break;
  182. }
  183. }
  184. GetDlgItem (IDC_DELETE_PERMANENTLY)->EnableWindow (!bEncryptionSelected);
  185. if ( bEncryptionSelected &&
  186. BST_CHECKED == SendDlgItemMessage (IDC_DELETE_PERMANENTLY, BM_GETCHECK) )
  187. {
  188. SendDlgItemMessage (IDC_DELETE_PERMANENTLY, BM_SETCHECK, BST_UNCHECKED);
  189. m_rCertTemplate.SetRemoveInvalidCertFromPersonalStore (false);
  190. }
  191. GetDlgItem (IDC_INCLUDE_SYMMETRIC_ALGORITHMS_CHECK)->EnableWindow (bEncryptionSelected);
  192. if ( !bEncryptionSelected )
  193. SendDlgItemMessage (IDC_INCLUDE_SYMMETRIC_ALGORITHMS_CHECK, BM_SETCHECK, BST_UNCHECKED);
  194. BOOL bEnableArchiveKeyCheck = bEncryptionSelected;
  195. if ( m_nProvDSSCnt > 0 )
  196. bEnableArchiveKeyCheck = FALSE;
  197. if ( bEnableArchiveKeyCheck )
  198. {
  199. GetDlgItem (IDC_ARCHIVE_KEY_CHECK)->EnableWindow (TRUE);
  200. }
  201. else
  202. {
  203. SendDlgItemMessage (IDC_ARCHIVE_KEY_CHECK, BM_SETCHECK, BST_UNCHECKED);
  204. OnArchiveKeyCheck (); // clear flag
  205. GetDlgItem (IDC_ARCHIVE_KEY_CHECK)->EnableWindow (FALSE);
  206. }
  207. }
  208. }
  209. HRESULT CTemplateV2RequestPropertyPage::EnumerateCSPs(DWORD dwMinKeySize)
  210. {
  211. _TRACE (1, L"Entering CTemplateV2RequestPropertyPage::EnumerateCSPs\n");
  212. HRESULT hr = S_OK;
  213. for (DWORD dwIndex = 0; ;dwIndex++)
  214. {
  215. DWORD cbName = 0;
  216. DWORD dwProvType = 0;
  217. if ( CryptEnumProviders (dwIndex, NULL, 0, &dwProvType, NULL, &cbName) )
  218. {
  219. PWSTR pszTypeName = new WCHAR[cbName];
  220. if ( pszTypeName )
  221. {
  222. if ( CryptEnumProviders (dwIndex, NULL, 0, &dwProvType,
  223. pszTypeName, &cbName) )
  224. {
  225. DWORD dwSigMaxKey = (DWORD) -1;
  226. DWORD dwKeyExMaxKey = (DWORD) -1;
  227. CSPGetMaxKeySupported (pszTypeName, dwProvType, dwSigMaxKey, dwKeyExMaxKey);
  228. // If either of these values is still -1, then it was not
  229. // set. Set to 0.
  230. if ( -1 == dwSigMaxKey )
  231. dwSigMaxKey = 0;
  232. if ( -1 == dwKeyExMaxKey )
  233. dwKeyExMaxKey = 0;
  234. CT_CSP_DATA* pNewData = new CT_CSP_DATA (pszTypeName,
  235. dwProvType, dwSigMaxKey, dwKeyExMaxKey);
  236. if ( pNewData )
  237. {
  238. m_CSPList.AddTail (pNewData);
  239. }
  240. }
  241. else
  242. {
  243. hr = HRESULT_FROM_WIN32 (GetLastError ());
  244. _TRACE (0, L"CryptEnumProviderTypes () failed: 0x%x\n", hr);
  245. break;
  246. }
  247. delete [] pszTypeName;
  248. }
  249. else
  250. hr = E_OUTOFMEMORY;
  251. }
  252. else
  253. {
  254. hr = HRESULT_FROM_WIN32 (GetLastError ());
  255. _TRACE (0, L"CryptEnumProviderTypes () failed: 0x%x\n", hr);
  256. break;
  257. }
  258. }
  259. int nCSPIndex = 0;
  260. CString szCSP;
  261. NormalizeCSPListBox (dwMinKeySize, false);
  262. CStringList invalidCSPs; // CSPs selected but not supporting the key size
  263. // Set the checks
  264. m_nProvDSSCnt = 0;
  265. nCSPIndex = 0;
  266. while ( SUCCEEDED (m_rCertTemplate.GetCSP (nCSPIndex, szCSP)) )
  267. {
  268. int nIndex = m_CSPListbox.FindString (-1, szCSP);
  269. if ( LB_ERR != nIndex )
  270. {
  271. m_CSPListbox.SetCheck (nIndex, BST_CHECKED);
  272. CT_CSP_DATA* pCSPData = (CT_CSP_DATA*) m_CSPListbox.GetItemData (nIndex);
  273. if ( pCSPData )
  274. {
  275. if ( PROV_DSS == pCSPData->m_dwProvType ||
  276. PROV_DSS_DH == pCSPData->m_dwProvType )
  277. {
  278. m_nProvDSSCnt++;
  279. }
  280. }
  281. }
  282. else
  283. {
  284. invalidCSPs.AddTail (szCSP);
  285. }
  286. nCSPIndex++;
  287. }
  288. for (POSITION nextPos = invalidCSPs.GetHeadPosition (); nextPos;)
  289. {
  290. CString szInvalidCSP = invalidCSPs.GetNext (nextPos);
  291. if ( !szInvalidCSP.IsEmpty () )
  292. {
  293. m_rCertTemplate.ModifyCSPList (szInvalidCSP, false); // remove
  294. }
  295. }
  296. EnableControls ();
  297. _TRACE (-1, L"Entering CTemplateV2RequestPropertyPage::EnumerateCSPs: 0x%x\n", hr);
  298. return hr;
  299. }
  300. void CTemplateV2RequestPropertyPage::OnSelchangePurposeCombo()
  301. {
  302. int nIndex = m_purposeCombo.GetCurSel ();
  303. if ( nIndex >= 0 )
  304. {
  305. // NTRAID# 278356 CertSRV: No CSPs in mmc certificate snapin advanced
  306. // option list with v2 templates that have ENC and SIG as purpose.
  307. switch (m_purposeCombo.GetItemData (nIndex))
  308. {
  309. case REQUEST_PURPOSE_SIGNATURE:
  310. m_rCertTemplate.SetEncryptionSignature (false);
  311. m_rCertTemplate.SetKeySpecSignature (true);
  312. break;
  313. case REQUEST_PURPOSE_ENCRYPTION:
  314. m_rCertTemplate.SetEncryptionSignature (true);
  315. m_rCertTemplate.SetKeySpecSignature (false);
  316. m_rCertTemplate.SetDigitalSignature (false);
  317. break;
  318. case REQUEST_PURPOSE_SIGNATURE_AND_ENCRYPTION:
  319. m_rCertTemplate.SetEncryptionSignature (true);
  320. m_rCertTemplate.SetKeySpecSignature (false);
  321. m_rCertTemplate.SetDigitalSignature (true);
  322. break;
  323. default:
  324. _ASSERT (0);
  325. break;
  326. }
  327. }
  328. int nSel = m_minKeySizeCombo.GetCurSel ();
  329. ASSERT (nSel >= 0);
  330. if ( nSel >= 0 )
  331. {
  332. DWORD dwMinKeySize = (DWORD) m_minKeySizeCombo.GetItemData (nSel);
  333. ASSERT (dwMinKeySize > 0);
  334. // Clear CSP list and add only values that correspond, saving checks
  335. NormalizeCSPListBox (dwMinKeySize, true);
  336. }
  337. SetModified ();
  338. m_rbIsDirty = true;
  339. EnableControls ();
  340. }
  341. void CTemplateV2RequestPropertyPage::AddKeySizeToCombo(DWORD dwValue, PCWSTR strValue, DWORD dwSizeToSelect)
  342. {
  343. int nIndex = m_minKeySizeCombo.AddString (strValue);
  344. if ( nIndex >= 0 )
  345. {
  346. m_minKeySizeCombo.SetItemData (nIndex, dwValue);
  347. if ( dwSizeToSelect == dwValue )
  348. m_minKeySizeCombo.SetCurSel (nIndex);
  349. }
  350. }
  351. void CTemplateV2RequestPropertyPage::OnExportPrivateKey()
  352. {
  353. bool bMakeExportable = (BST_CHECKED == SendDlgItemMessage (IDC_EXPORT_PRIVATE_KEY, BM_GETCHECK));
  354. m_rCertTemplate.MakePrivateKeyExportable (bMakeExportable);
  355. SetModified ();
  356. m_rbIsDirty = true;
  357. }
  358. void CTemplateV2RequestPropertyPage::OnArchiveKeyCheck()
  359. {
  360. bool bAllowKeyArchival = (BST_CHECKED == SendDlgItemMessage (IDC_ARCHIVE_KEY_CHECK, BM_GETCHECK));
  361. m_rCertTemplate.AllowPrivateKeyArchival (bAllowKeyArchival);
  362. SetModified ();
  363. m_rbIsDirty = true;
  364. }
  365. void CTemplateV2RequestPropertyPage::OnIncludeSymmetricAlgorithmsCheck()
  366. {
  367. bool bInclude =
  368. (BST_CHECKED == SendDlgItemMessage (IDC_INCLUDE_SYMMETRIC_ALGORITHMS_CHECK, BM_GETCHECK));
  369. m_rCertTemplate.IncludeSymmetricAlgorithems (bInclude);
  370. SetModified ();
  371. m_rbIsDirty = true;
  372. }
  373. void CTemplateV2RequestPropertyPage::OnSelchangeMinimumKeysizeValue()
  374. {
  375. SetModified ();
  376. m_rbIsDirty = true;
  377. int nSel = m_minKeySizeCombo.GetCurSel ();
  378. ASSERT (nSel >= 0);
  379. if ( nSel >= 0 )
  380. {
  381. DWORD dwMinKeySize = (DWORD) m_minKeySizeCombo.GetItemData (nSel);
  382. ASSERT (dwMinKeySize > 0);
  383. HRESULT hr = m_rCertTemplate.SetMinimumKeySizeValue (dwMinKeySize);
  384. if ( FAILED (hr) )
  385. {
  386. CString text;
  387. CString caption;
  388. CThemeContextActivator activator;
  389. VERIFY (caption.LoadString (IDS_CERTTMPL));
  390. text.FormatMessage (IDS_CANNOT_WRITE_MINKEYSIZE, hr);
  391. MessageBox (text, caption, MB_OK | MB_ICONWARNING);
  392. }
  393. // Clear CSP list and add only values that correspond, saving checks
  394. NormalizeCSPListBox (dwMinKeySize, true);
  395. }
  396. }
  397. void CTemplateV2RequestPropertyPage::OnCheckChange()
  398. {
  399. int nSel = m_CSPListbox.GetCurSel ();
  400. if ( nSel >= 0 )
  401. {
  402. CString szCSPName;
  403. m_CSPListbox.GetText (nSel, szCSPName);
  404. if ( !szCSPName.IsEmpty () )
  405. {
  406. HRESULT hr = S_OK;
  407. if ( BST_CHECKED == m_CSPListbox.GetCheck (nSel) )
  408. {
  409. hr = m_rCertTemplate.ModifyCSPList (szCSPName, true); // add
  410. CT_CSP_DATA* pData = (CT_CSP_DATA*) m_CSPListbox.GetItemData (nSel);
  411. if ( pData )
  412. {
  413. if ( PROV_DSS == pData->m_dwProvType || PROV_DSS_DH == pData->m_dwProvType )
  414. m_nProvDSSCnt++;
  415. }
  416. }
  417. else
  418. {
  419. hr = m_rCertTemplate.ModifyCSPList (szCSPName, false); // remove
  420. CT_CSP_DATA* pData = (CT_CSP_DATA*) m_CSPListbox.GetItemData (nSel);
  421. if ( pData )
  422. {
  423. if ( PROV_DSS == pData->m_dwProvType || PROV_DSS_DH == pData->m_dwProvType )
  424. m_nProvDSSCnt--;
  425. }
  426. }
  427. if ( SUCCEEDED (hr) )
  428. {
  429. SetModified ();
  430. m_rbIsDirty = true;
  431. }
  432. }
  433. }
  434. EnableControls ();
  435. }
  436. void CTemplateV2RequestPropertyPage::DoContextHelp (HWND hWndControl)
  437. {
  438. _TRACE(1, L"Entering CTemplateV2RequestPropertyPage::DoContextHelp\n");
  439. switch (::GetDlgCtrlID (hWndControl))
  440. {
  441. case IDC_STATIC:
  442. case IDC_MINIMUM_KEYSIZE_LABEL:
  443. break;
  444. default:
  445. // Display context help for a control
  446. if ( !::WinHelp (
  447. hWndControl,
  448. GetContextHelpFile (),
  449. HELP_WM_HELP,
  450. (DWORD_PTR) g_aHelpIDs_IDD_TEMPLATE_V2_REQUEST) )
  451. {
  452. _TRACE(0, L"WinHelp () failed: 0x%x\n", GetLastError ());
  453. }
  454. break;
  455. }
  456. _TRACE(-1, L"Leaving CTemplateV2RequestPropertyPage::DoContextHelp\n");
  457. }
  458. void CTemplateV2RequestPropertyPage::OnUserInputRequiredForAutoenrollment()
  459. {
  460. bool bSet = BST_CHECKED == SendDlgItemMessage (
  461. IDC_USER_INPUT_REQUIRED_FOR_AUTOENROLLMENT, BM_GETCHECK);
  462. m_rCertTemplate.SetUserInteractionRequired (bSet);
  463. SetModified ();
  464. m_rbIsDirty = true;
  465. }
  466. void CTemplateV2RequestPropertyPage::OnDeletePermanently()
  467. {
  468. m_rCertTemplate.SetRemoveInvalidCertFromPersonalStore (
  469. BST_CHECKED == SendDlgItemMessage (IDC_DELETE_PERMANENTLY, BM_GETCHECK));
  470. SetModified ();
  471. m_rbIsDirty = true;
  472. }
  473. HRESULT CTemplateV2RequestPropertyPage::CSPGetMaxKeySupported (
  474. PCWSTR pszProvider,
  475. DWORD dwProvType,
  476. DWORD& rdwSigMaxKey,
  477. DWORD& rdwKeyExMaxKey)
  478. {
  479. _TRACE (1, L"Entering CTemplateV2RequestPropertyPage::CSPGetMaxKeySupported (%s)\n",
  480. pszProvider);
  481. HRESULT hr = S_OK;
  482. HCRYPTPROV hProv = 0;
  483. BOOL bResult = ::CryptAcquireContext (&hProv,
  484. NULL,
  485. pszProvider,
  486. dwProvType,
  487. CRYPT_VERIFYCONTEXT | CRYPT_SILENT);
  488. if ( bResult )
  489. {
  490. PROV_ENUMALGS_EX EnumAlgs; // Structure to hold information on
  491. // a supported algorithm
  492. DWORD dFlag = CRYPT_FIRST; // Flag indicating that the first
  493. // supported algorithm is to be
  494. // enumerated. Changed to 0 after the
  495. // first call to the function.
  496. DWORD cbData = sizeof(PROV_ENUMALGS_EX);
  497. while (CryptGetProvParam(
  498. hProv, // handle to an open cryptographic provider
  499. PP_ENUMALGS_EX,
  500. (BYTE *)&EnumAlgs, // information on the next algorithm
  501. &cbData, // number of bytes in the PROV_ENUMALGS_EX
  502. dFlag)) // flag to indicate whether this is a first or
  503. // subsequent algorithm supported by the
  504. // CSP.
  505. {
  506. if ( ALG_CLASS_SIGNATURE == GET_ALG_CLASS (EnumAlgs.aiAlgid) )
  507. rdwSigMaxKey = EnumAlgs.dwMaxLen;
  508. if ( ALG_CLASS_KEY_EXCHANGE == GET_ALG_CLASS (EnumAlgs.aiAlgid) )
  509. rdwKeyExMaxKey = EnumAlgs.dwMaxLen;
  510. if ( -1 != rdwSigMaxKey && -1 != rdwKeyExMaxKey )
  511. break; // both have been set
  512. dFlag = 0; // Set to 0 after the first call,
  513. } // end of while loop. When all of the supported algorithms have
  514. // been enumerated, the function returns FALSE.
  515. ::CryptReleaseContext (hProv, 0);
  516. }
  517. else
  518. {
  519. DWORD dwErr = GetLastError ();
  520. _TRACE (0, L"CryptAcquireContext () failed: 0x%x\n", dwErr);
  521. hr = HRESULT_FROM_WIN32 (dwErr);
  522. }
  523. _TRACE (-1, L"Leaving CTemplateV2RequestPropertyPage::CSPGetMaxKeySupported (%s)\n",
  524. pszProvider);
  525. return hr;
  526. }
  527. // NTRAID# 313348 Cert Template UI: Need to warn the user if the template
  528. // minimum key length is not supported by the CSPs
  529. void CTemplateV2RequestPropertyPage::NormalizeCSPListBox (DWORD dwMinKeySize, bool bSetChecks)
  530. {
  531. // Save the checked CSPs
  532. CStringList checkedCSPList;
  533. if ( bSetChecks )
  534. {
  535. int nCnt = m_CSPListbox.GetCount ();
  536. while (nCnt > 0)
  537. {
  538. nCnt--;
  539. if ( BST_CHECKED == m_CSPListbox.GetCheck (nCnt) )
  540. {
  541. CString szText;
  542. m_CSPListbox.GetText (nCnt, szText);
  543. checkedCSPList.AddTail (szText);
  544. m_rCertTemplate.ModifyCSPList (szText, false); // remove
  545. }
  546. }
  547. }
  548. // Remove all CSPs
  549. m_CSPListbox.ResetContent ();
  550. bool bSignatureOnly = false;
  551. int nIndex = m_purposeCombo.GetCurSel ();
  552. if ( nIndex >= 0 )
  553. bSignatureOnly = (REQUEST_PURPOSE_SIGNATURE == m_purposeCombo.GetItemData (nIndex));
  554. // Fill the listbox with conforming CSPs
  555. for (POSITION nextPos = m_CSPList.GetHeadPosition (); nextPos; )
  556. {
  557. CT_CSP_DATA* pCSPData = m_CSPList.GetNext (nextPos);
  558. if ( pCSPData )
  559. {
  560. bool bAddString = false;
  561. if ( bSignatureOnly && pCSPData->m_dwSigMaxKeySize >= dwMinKeySize )
  562. bAddString = true;
  563. else if ( pCSPData->m_dwKeyExMaxKeySize >= dwMinKeySize )
  564. bAddString = true;
  565. if ( bAddString )
  566. {
  567. nIndex = m_CSPListbox.AddString (pCSPData->m_szName);
  568. if ( nIndex < 0 )
  569. {
  570. _TRACE (0, L"AddString (%s) failed: %d\n", nIndex);
  571. break;
  572. }
  573. else
  574. {
  575. m_CSPListbox.SetItemData (nIndex, (DWORD_PTR) pCSPData);
  576. }
  577. }
  578. }
  579. }
  580. if ( bSetChecks )
  581. {
  582. m_nProvDSSCnt = 0;
  583. // Restore saved checks, where possible
  584. for (POSITION nextPos = checkedCSPList.GetHeadPosition (); nextPos; )
  585. {
  586. CString szText = checkedCSPList.GetNext (nextPos);
  587. nIndex = m_CSPListbox.FindStringExact (-1, szText);
  588. if ( LB_ERR != nIndex )
  589. {
  590. m_CSPListbox.SetCheck (nIndex, BST_CHECKED);
  591. m_rCertTemplate.ModifyCSPList (szText, true); // add
  592. CT_CSP_DATA* pCSPData = (CT_CSP_DATA*) m_CSPListbox.GetItemData (nIndex);
  593. if ( pCSPData )
  594. {
  595. if ( PROV_DSS == pCSPData->m_dwProvType ||
  596. PROV_DSS_DH == pCSPData->m_dwProvType )
  597. {
  598. m_nProvDSSCnt++;
  599. }
  600. }
  601. }
  602. }
  603. }
  604. }