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.

247 lines
5.4 KiB

  1. //+-------------------------------------------------------------------------
  2. // Microsoft Windows
  3. //
  4. // Copyright (C) Microsoft Corporation, 1995 - 1996
  5. //
  6. // File: pkcs8ex.cpp
  7. //
  8. // Contents: Private Key Save Test
  9. //
  10. // See Usage() for list of save options.
  11. //
  12. // Functions: main
  13. //
  14. // History: 11-May-96 philh created
  15. //--------------------------------------------------------------------------
  16. #include <windows.h>
  17. #include <assert.h>
  18. #include "wincrypt.h"
  19. #include "certtest.h"
  20. #include <stdlib.h>
  21. #include <stdio.h>
  22. #include <string.h>
  23. #include <memory.h>
  24. #include <time.h>
  25. static struct
  26. {
  27. LPCSTR pszName;
  28. LPCWSTR pwszKeyTitle;
  29. DWORD dwKeySpec;
  30. } KeyTypes[] = {
  31. "Sign", L"Signature", AT_SIGNATURE,
  32. "Xchg", L"Exchange", AT_KEYEXCHANGE
  33. };
  34. #define NKEYTYPES (sizeof(KeyTypes)/sizeof(KeyTypes[0]))
  35. static void Usage(void)
  36. {
  37. int i;
  38. printf("Usage: pkcs8ex [options] <Filename> <KeyType>\n");
  39. printf("Options are:\n");
  40. printf(" -p<name> - Crypto provider name (if not default)\n");
  41. printf(" -c<name> - Crypto key container name\n");
  42. printf(" -d - Delete from provider after saving\n");
  43. printf(" -h - This message\n");
  44. printf("\n");
  45. printf("KeyType (case insensitive):\n");
  46. for (i = 0; i < NKEYTYPES; i++)
  47. printf(" %s\n", KeyTypes[i].pszName);
  48. printf("\n");
  49. }
  50. int _cdecl main(int argc, char * argv[])
  51. {
  52. int ReturnStatus;
  53. HCRYPTPROV hProv = 0;
  54. HANDLE hFile = INVALID_HANDLE_VALUE;
  55. DWORD dwProvType = PROV_RSA_FULL;
  56. BOOL fDelete = FALSE;
  57. LPSTR pszContainer = NULL;
  58. LPSTR pszFilename = NULL;
  59. BYTE *pbKey = NULL;
  60. DWORD cbKey = 0;
  61. LPSTR pszKeyType = NULL;
  62. int KeyIdx = 0;
  63. DWORD numBytesWritten;
  64. DWORD dwFlags;
  65. while (--argc>0)
  66. {
  67. if (**++argv == '-')
  68. {
  69. switch(argv[0][1])
  70. {
  71. case 'd':
  72. fDelete = TRUE;
  73. break;
  74. case 'p':
  75. dwProvType = strtoul( argv[0]+2, NULL, 10);
  76. break;
  77. case 'c':
  78. pszContainer = argv[0]+2;
  79. if (*pszContainer == '\0') {
  80. printf("Need to specify crypto key container name\n");
  81. goto BadUsage;
  82. }
  83. break;
  84. case 'h':
  85. default:
  86. goto BadUsage;
  87. }
  88. } else {
  89. if (pszFilename == NULL)
  90. pszFilename = argv[0];
  91. else if(pszKeyType == NULL)
  92. pszKeyType = argv[0];
  93. else {
  94. printf("Too many arguments\n");
  95. goto BadUsage;
  96. }
  97. }
  98. }
  99. printf("command line: %s\n", GetCommandLine());
  100. if (pszFilename == NULL) {
  101. printf("missing Filename\n");
  102. goto BadUsage;
  103. }
  104. if (pszKeyType) {
  105. for (KeyIdx = 0; KeyIdx < NKEYTYPES; KeyIdx++) {
  106. if (_stricmp(pszKeyType, KeyTypes[KeyIdx].pszName) == 0)
  107. break;
  108. }
  109. if (KeyIdx >= NKEYTYPES) {
  110. printf("Bad KeyType: %s\n", pszKeyType);
  111. goto BadUsage;
  112. }
  113. } else {
  114. printf("missing KeyType\n");
  115. goto BadUsage;
  116. }
  117. if (!CryptAcquireContext(
  118. &hProv,
  119. pszContainer,
  120. NULL, // pszProvider
  121. dwProvType,
  122. 0 // dwFlags
  123. )) {
  124. PrintLastError("CryptAcquireContext\n");
  125. goto ErrorReturn;
  126. }
  127. hFile = CreateFileA(
  128. pszFilename,
  129. GENERIC_READ | GENERIC_WRITE,
  130. FILE_SHARE_READ,
  131. NULL, // lpsa
  132. CREATE_ALWAYS,
  133. FILE_ATTRIBUTE_NORMAL,
  134. NULL // hTemplateFile
  135. );
  136. if (hFile == INVALID_HANDLE_VALUE) {
  137. printf("can't open %s\n", pszFilename);
  138. printf("Failed");
  139. goto ErrorReturn;
  140. }
  141. if (!CryptExportPKCS8(
  142. hProv,
  143. KeyTypes[KeyIdx].dwKeySpec,
  144. szOID_RSA_RSA,
  145. 0,
  146. NULL,
  147. NULL,
  148. &cbKey)) {
  149. PrintLastError("CryptExportPKCS8");
  150. goto ErrorReturn;
  151. }
  152. if (NULL == (pbKey = (BYTE *) TestAlloc(cbKey))) {
  153. printf("memory allocation error\n");
  154. goto ErrorReturn;
  155. }
  156. /*if (fDelete)
  157. dwFlags = DELETE_KEYSET;
  158. else
  159. dwFlags = 0;*/
  160. if (!CryptExportPKCS8(
  161. hProv,
  162. KeyTypes[KeyIdx].dwKeySpec,
  163. szOID_RSA_RSA,
  164. 0,
  165. NULL,
  166. pbKey,
  167. &cbKey)) {
  168. PrintLastError("CryptExportPKCS8");
  169. goto ErrorReturn;
  170. }
  171. if (!WriteFile(
  172. hFile,
  173. pbKey,
  174. cbKey,
  175. &numBytesWritten,
  176. NULL)) {
  177. PrintLastError("WriteFile");
  178. goto ErrorReturn;
  179. }
  180. if (fDelete) {
  181. // Delete the existing keys
  182. CryptReleaseContext(hProv, 0);
  183. printf("Deleting existing private keys\n");
  184. // Note: for CRYPT_DELETEKEYSET, the returned hProv is undefined
  185. // and must not be released.
  186. if (!CryptAcquireContext(
  187. &hProv,
  188. pszContainer,
  189. NULL, // pszProvider
  190. dwProvType,
  191. CRYPT_DELETEKEYSET
  192. )) {
  193. PrintLastError("CryptAcquireContext(CRYPT_DELETEKEYSET)");
  194. hProv = 0;
  195. goto ErrorReturn;
  196. }
  197. hProv = 0;
  198. }
  199. ReturnStatus = 0;
  200. goto CommonReturn;
  201. BadUsage:
  202. Usage();
  203. ErrorReturn:
  204. ReturnStatus = -1;
  205. if (hFile != INVALID_HANDLE_VALUE) {
  206. CloseHandle(hFile);
  207. hFile = INVALID_HANDLE_VALUE;
  208. DeleteFile(pszFilename);
  209. }
  210. CommonReturn:
  211. if (hFile != INVALID_HANDLE_VALUE)
  212. CloseHandle(hFile);
  213. if (hProv)
  214. CryptReleaseContext(hProv, 0);
  215. if (pbKey)
  216. TestFree(pbKey);
  217. return ReturnStatus;
  218. }