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.

619 lines
16 KiB

  1. //+---------------------------------------------------------------------------
  2. //
  3. // Microsoft Windows
  4. // Copyright (C) Microsoft Corporation, 1992 - 1995.
  5. //
  6. // File: stubs.c
  7. //
  8. // Contents:
  9. //
  10. // Classes:
  11. //
  12. // Functions:
  13. //
  14. // History: 8-01-95 RichardW Created
  15. //
  16. //----------------------------------------------------------------------------
  17. #include "sslp.h"
  18. #include <cert509.h>
  19. #include <rsa.h>
  20. CHAR CertTag[ 13 ] = { 0x04, 0x0b, 'c', 'e', 'r', 't', 'i', 'f', 'i', 'c', 'a', 't', 'e' };
  21. // Nonstandard extension, function/data pointer conversion in expression
  22. #pragma warning (disable: 4152)
  23. SecurityFunctionTableW SPFunctionTable = {
  24. SECURITY_SUPPORT_PROVIDER_INTERFACE_VERSION,
  25. EnumerateSecurityPackagesW,
  26. NULL,
  27. AcquireCredentialsHandleW,
  28. FreeCredentialsHandle,
  29. NULL,
  30. InitializeSecurityContextW,
  31. AcceptSecurityContext,
  32. CompleteAuthToken,
  33. DeleteSecurityContext,
  34. ApplyControlToken,
  35. QueryContextAttributesW,
  36. ImpersonateSecurityContext,
  37. RevertSecurityContext,
  38. MakeSignature,
  39. VerifySignature,
  40. FreeContextBuffer,
  41. QuerySecurityPackageInfoW,
  42. SealMessage,
  43. UnsealMessage,
  44. NULL, /* GrantProxyW */
  45. NULL, /* RevokeProxyW */
  46. NULL, /* InvokeProxyW */
  47. NULL, /* RenewProxyW */
  48. QuerySecurityContextToken,
  49. SealMessage,
  50. UnsealMessage,
  51. SetContextAttributesW
  52. };
  53. SecurityFunctionTableA SPFunctionTableA = {
  54. SECURITY_SUPPORT_PROVIDER_INTERFACE_VERSION,
  55. EnumerateSecurityPackagesA,
  56. NULL,
  57. AcquireCredentialsHandleA,
  58. FreeCredentialsHandle,
  59. NULL,
  60. InitializeSecurityContextA,
  61. AcceptSecurityContext,
  62. CompleteAuthToken,
  63. DeleteSecurityContext,
  64. ApplyControlToken,
  65. QueryContextAttributesA,
  66. ImpersonateSecurityContext,
  67. RevertSecurityContext,
  68. MakeSignature,
  69. VerifySignature,
  70. FreeContextBuffer,
  71. QuerySecurityPackageInfoA,
  72. SealMessage,
  73. UnsealMessage,
  74. NULL, /* GrantProxyA */
  75. NULL, /* RevokeProxyA */
  76. NULL, /* InvokeProxyA */
  77. NULL, /* RenewProxyA */
  78. QuerySecurityContextToken,
  79. SealMessage,
  80. UnsealMessage,
  81. SetContextAttributesA
  82. };
  83. PSecurityFunctionTableW SEC_ENTRY
  84. InitSecurityInterfaceW(
  85. VOID )
  86. {
  87. return(&SPFunctionTable);
  88. }
  89. PSecurityFunctionTableA SEC_ENTRY
  90. InitSecurityInterfaceA(
  91. VOID )
  92. {
  93. return(&SPFunctionTableA);
  94. }
  95. SECURITY_STATUS SEC_ENTRY
  96. FreeContextBuffer(
  97. void SEC_FAR * pvContextBuffer
  98. )
  99. {
  100. SPExternalFree( pvContextBuffer );
  101. return(SEC_E_OK);
  102. }
  103. SECURITY_STATUS SEC_ENTRY
  104. SecurityPackageControl(
  105. SEC_WCHAR SEC_FAR * pszPackageName,
  106. unsigned long dwFunctionCode,
  107. unsigned long cbInputBuffer,
  108. unsigned char SEC_FAR * pbInputBuffer,
  109. unsigned long SEC_FAR * pcbOutputBuffer,
  110. unsigned char SEC_FAR * pbOutputBuffer)
  111. {
  112. UNREFERENCED_PARAMETER(pszPackageName);
  113. UNREFERENCED_PARAMETER(dwFunctionCode);
  114. UNREFERENCED_PARAMETER(cbInputBuffer);
  115. UNREFERENCED_PARAMETER(pbInputBuffer);
  116. UNREFERENCED_PARAMETER(pcbOutputBuffer);
  117. UNREFERENCED_PARAMETER(pbOutputBuffer);
  118. return(SEC_E_UNSUPPORTED_FUNCTION);
  119. }
  120. SECURITY_STATUS PctTranslateError(SP_STATUS spRet)
  121. {
  122. if(HRESULT_FACILITY(spRet) == FACILITY_SECURITY)
  123. {
  124. return (spRet);
  125. }
  126. switch(spRet) {
  127. case PCT_ERR_OK: return SEC_E_OK;
  128. case PCT_ERR_BAD_CERTIFICATE: return SEC_E_INVALID_TOKEN;
  129. case PCT_ERR_CLIENT_AUTH_FAILED: return SEC_E_INVALID_TOKEN;
  130. case PCT_ERR_ILLEGAL_MESSAGE: return SEC_E_INVALID_TOKEN;
  131. case PCT_ERR_INTEGRITY_CHECK_FAILED: return SEC_E_MESSAGE_ALTERED;
  132. case PCT_ERR_SERVER_AUTH_FAILED: return SEC_E_INVALID_TOKEN;
  133. case PCT_ERR_SPECS_MISMATCH: return SEC_E_ALGORITHM_MISMATCH;
  134. case PCT_ERR_SSL_STYLE_MSG: return SEC_E_INVALID_TOKEN;
  135. case SEC_I_INCOMPLETE_CREDENTIALS: return SEC_I_INCOMPLETE_CREDENTIALS;
  136. case PCT_ERR_RENEGOTIATE: return SEC_I_RENEGOTIATE;
  137. case PCT_ERR_UNKNOWN_CREDENTIAL: return SEC_E_UNKNOWN_CREDENTIALS;
  138. case CERT_E_UNTRUSTEDROOT: return SEC_E_UNTRUSTED_ROOT;
  139. case CERT_E_EXPIRED: return SEC_E_CERT_EXPIRED;
  140. case CERT_E_VALIDITYPERIODNESTING: return SEC_E_CERT_EXPIRED;
  141. case CERT_E_REVOKED: return CRYPT_E_REVOKED;
  142. case CERT_E_CN_NO_MATCH: return SEC_E_WRONG_PRINCIPAL;
  143. case PCT_INT_BAD_CERT: return SEC_E_INVALID_TOKEN;
  144. case PCT_INT_CLI_AUTH: return SEC_E_INVALID_TOKEN;
  145. case PCT_INT_ILLEGAL_MSG: return SEC_E_INVALID_TOKEN;
  146. case PCT_INT_SPECS_MISMATCH: return SEC_E_ALGORITHM_MISMATCH;
  147. case PCT_INT_INCOMPLETE_MSG: return SEC_E_INCOMPLETE_MESSAGE;
  148. case PCT_INT_MSG_ALTERED: return SEC_E_MESSAGE_ALTERED;
  149. case PCT_INT_INTERNAL_ERROR: return SEC_E_INTERNAL_ERROR;
  150. case PCT_INT_DATA_OVERFLOW: return SEC_E_INTERNAL_ERROR;
  151. case SEC_E_INCOMPLETE_CREDENTIALS: return SEC_E_INCOMPLETE_CREDENTIALS;
  152. case PCT_INT_RENEGOTIATE: return SEC_I_RENEGOTIATE;
  153. case PCT_INT_UNKNOWN_CREDENTIAL: return SEC_E_UNKNOWN_CREDENTIALS;
  154. case PCT_INT_BUFF_TOO_SMALL: return SEC_E_BUFFER_TOO_SMALL;
  155. case SEC_E_BUFFER_TOO_SMALL: return SEC_E_BUFFER_TOO_SMALL;
  156. default: return SEC_E_INTERNAL_ERROR;
  157. }
  158. }
  159. //+---------------------------------------------------------------------------
  160. //
  161. // Function: SslGenerateRandomBits
  162. //
  163. // Synopsis: Hook for setup to get a good random stream
  164. //
  165. // Arguments: [pRandomData] --
  166. // [cRandomData] --
  167. //
  168. //
  169. // Notes:
  170. //
  171. //----------------------------------------------------------------------------
  172. VOID
  173. WINAPI
  174. SslGenerateRandomBits(
  175. PUCHAR pRandomData,
  176. LONG cRandomData
  177. )
  178. {
  179. if(!SchannelInit(TRUE))
  180. {
  181. return;
  182. }
  183. (void)GenerateRandomBits(pRandomData, (ULONG)cRandomData);
  184. }
  185. //+---------------------------------------------------------------------------
  186. //
  187. // Function: SslGenerateKeyPair
  188. //
  189. // Synopsis: Generates a public/private key pair, protected by password
  190. //
  191. // Arguments: [pCerts] --
  192. // [pszDN] --
  193. // [pszPassword] --
  194. // [Bits] --
  195. //
  196. // Notes:
  197. //
  198. //----------------------------------------------------------------------------
  199. BOOL
  200. WINAPI
  201. SslGenerateKeyPair(
  202. PSSL_CREDENTIAL_CERTIFICATE pCerts,
  203. PSTR pszDN,
  204. PSTR pszPassword,
  205. DWORD Bits )
  206. {
  207. if(!SchannelInit(TRUE))
  208. {
  209. return FALSE;
  210. }
  211. return GenerateKeyPair(pCerts, pszDN, pszPassword, Bits);
  212. }
  213. //+---------------------------------------------------------------------------
  214. //
  215. // Function: SslGetMaximumKeySize
  216. //
  217. // Synopsis: Returns maximum public key size
  218. //
  219. // Arguments: [Reserved] --
  220. //
  221. // Notes:
  222. //
  223. //----------------------------------------------------------------------------
  224. DWORD
  225. WINAPI
  226. SslGetMaximumKeySize(
  227. DWORD Reserved )
  228. {
  229. UNREFERENCED_PARAMETER(Reserved);
  230. return( 2048 );
  231. }
  232. //+---------------------------------------------------------------------------
  233. //
  234. // Function: SslFreeCertificate
  235. //
  236. // Synopsis: Frees a certificate created from SslCrackCertificate
  237. //
  238. // Arguments: [pCertificate] --
  239. //
  240. // Notes:
  241. //
  242. //----------------------------------------------------------------------------
  243. VOID
  244. WINAPI
  245. SslFreeCertificate(
  246. PX509Certificate pCertificate)
  247. {
  248. if ( pCertificate )
  249. {
  250. SPExternalFree(pCertificate->pPublicKey);
  251. SPExternalFree(pCertificate);
  252. }
  253. }
  254. //+---------------------------------------------------------------------------
  255. //
  256. // Function: SslCrackCertificate
  257. //
  258. // Synopsis: Cracks a X509 certificate into remotely easy format
  259. //
  260. // Arguments: [pbCertificate] --
  261. // [cbCertificate] --
  262. // [dwFlags] --
  263. // [ppCertificate] --
  264. //
  265. // Notes:
  266. //
  267. //----------------------------------------------------------------------------
  268. BOOL
  269. WINAPI
  270. SslCrackCertificate(
  271. PUCHAR pbCertificate,
  272. DWORD cbCertificate,
  273. DWORD dwFlags,
  274. PX509Certificate * ppCertificate)
  275. {
  276. PX509Certificate pResult = NULL;
  277. PCCERT_CONTEXT pContext = NULL;
  278. DWORD cbIssuer;
  279. DWORD cbSubject;
  280. if(!SchannelInit(TRUE))
  281. {
  282. return FALSE;
  283. }
  284. if (dwFlags & CF_CERT_FROM_FILE)
  285. {
  286. if (cbCertificate < CERT_HEADER_LEN + 1 )
  287. {
  288. goto error;
  289. }
  290. //
  291. // Sleazy quick check. Some CAs wrap certs in a cert wrapper.
  292. // Some don't. Some do both, but we won't mention any names.
  293. // Quick check for the wrapper tag. If so, scoot in by enough
  294. // to bypass it (17 bytes. Sheesh).
  295. //
  296. if ( memcmp( pbCertificate + 4, CertTag, sizeof( CertTag ) ) == 0 )
  297. {
  298. pbCertificate += CERT_HEADER_LEN;
  299. cbCertificate -= CERT_HEADER_LEN;
  300. }
  301. }
  302. pContext = CertCreateCertificateContext(X509_ASN_ENCODING, pbCertificate, cbCertificate);
  303. if(pContext == NULL)
  304. {
  305. SP_LOG_RESULT(GetLastError());
  306. goto error;
  307. }
  308. if(0 >= (cbSubject = CertNameToStrA(pContext->dwCertEncodingType,
  309. &pContext->pCertInfo->Subject,
  310. CERT_X500_NAME_STR | CERT_NAME_STR_NO_PLUS_FLAG,
  311. NULL, 0)))
  312. {
  313. SP_LOG_RESULT(GetLastError());
  314. goto error;
  315. }
  316. if(0 >= (cbIssuer = CertNameToStrA(pContext->dwCertEncodingType,
  317. &pContext->pCertInfo->Issuer,
  318. CERT_X500_NAME_STR | CERT_NAME_STR_NO_PLUS_FLAG,
  319. NULL, 0)))
  320. {
  321. SP_LOG_RESULT(GetLastError());
  322. goto error;
  323. }
  324. pResult = SPExternalAlloc(sizeof(X509Certificate) + cbIssuer + cbSubject + 2);
  325. if(pResult == NULL)
  326. {
  327. goto error;
  328. }
  329. pResult->pPublicKey = NULL;
  330. pResult->pszIssuer = (LPSTR)(pResult + 1);
  331. pResult->pszSubject = pResult->pszIssuer + cbIssuer;
  332. pResult->Version = pContext->pCertInfo->dwVersion;
  333. memcpy(pResult->SerialNumber,
  334. pContext->pCertInfo->SerialNumber.pbData,
  335. min(sizeof(pResult->SerialNumber), pContext->pCertInfo->SerialNumber.cbData));
  336. pResult->ValidFrom = pContext->pCertInfo->NotBefore;
  337. pResult->ValidUntil = pContext->pCertInfo->NotAfter;
  338. if(0 >= CertNameToStrA(pContext->dwCertEncodingType,
  339. &pContext->pCertInfo->Issuer,
  340. CERT_X500_NAME_STR | CERT_NAME_STR_NO_PLUS_FLAG,
  341. pResult->pszIssuer, cbIssuer))
  342. {
  343. SP_LOG_RESULT(GetLastError());
  344. goto error;
  345. }
  346. if(0 >= CertNameToStrA(pContext->dwCertEncodingType,
  347. &pContext->pCertInfo->Subject,
  348. CERT_X500_NAME_STR | CERT_NAME_STR_NO_PLUS_FLAG,
  349. pResult->pszSubject, cbSubject))
  350. {
  351. SP_LOG_RESULT(GetLastError());
  352. goto error;
  353. }
  354. {
  355. BSAFE_PUB_KEY *pk;
  356. PUBLICKEY * pPubKey = NULL;
  357. SP_STATUS pctRet;
  358. pResult->pPublicKey = SPExternalAlloc(sizeof(PctPublicKey) + sizeof(BSAFE_PUB_KEY));
  359. if(pResult->pPublicKey == NULL)
  360. {
  361. goto error;
  362. }
  363. pResult->pPublicKey->Type = 0;
  364. pResult->pPublicKey->cbKey = sizeof(BSAFE_PUB_KEY);
  365. pk = (BSAFE_PUB_KEY *)pResult->pPublicKey->pKey;
  366. pk->magic = RSA1;
  367. pctRet = SPPublicKeyFromCert(pContext, &pPubKey, NULL);
  368. if(pctRet == PCT_ERR_OK)
  369. {
  370. if(pPubKey->pPublic->aiKeyAlg == CALG_RSA_KEYX)
  371. {
  372. RSAPUBKEY *pRsaKey = (RSAPUBKEY *)(pPubKey->pPublic + 1);
  373. pk->keylen = pRsaKey->bitlen/8;
  374. pk->bitlen = pRsaKey->bitlen;
  375. pk->datalen = pk->bitlen/8 - 1;
  376. pk->pubexp = pRsaKey->pubexp;
  377. }
  378. else
  379. {
  380. DHPUBKEY *pDHKey = (DHPUBKEY *)(pPubKey->pPublic + 1);
  381. pk->keylen = pDHKey->bitlen/8;
  382. pk->bitlen = pDHKey->bitlen/8;
  383. pk->datalen = pk->bitlen/8 - 1;
  384. pk->pubexp = 0;
  385. }
  386. SPExternalFree(pPubKey);
  387. }
  388. else
  389. {
  390. goto error;
  391. }
  392. }
  393. CertFreeCertificateContext(pContext);
  394. *ppCertificate = pResult;
  395. return TRUE;
  396. error:
  397. if(pContext)
  398. {
  399. CertFreeCertificateContext(pContext);
  400. }
  401. if(pResult)
  402. {
  403. if(pResult->pPublicKey)
  404. {
  405. SPExternalFree(pResult->pPublicKey);
  406. }
  407. SPExternalFree(pResult);
  408. }
  409. return FALSE;
  410. }
  411. //+---------------------------------------------------------------------------
  412. //
  413. // Function: SslLoadCertificate
  414. //
  415. // Synopsis: Not supported.
  416. //
  417. // Notes:
  418. //
  419. //----------------------------------------------------------------------------
  420. BOOL
  421. WINAPI
  422. SslLoadCertificate(
  423. PUCHAR pbCertificate,
  424. DWORD cbCertificate,
  425. BOOL AddToWellKnownKeys)
  426. {
  427. UNREFERENCED_PARAMETER(pbCertificate);
  428. UNREFERENCED_PARAMETER(cbCertificate);
  429. UNREFERENCED_PARAMETER(AddToWellKnownKeys);
  430. return FALSE;
  431. }
  432. BOOL
  433. SslGetClientProcess(ULONG *pProcessID)
  434. {
  435. SECPKG_CALL_INFO CallInfo;
  436. if(LsaTable == NULL)
  437. {
  438. *pProcessID = GetCurrentProcessId();
  439. return TRUE;
  440. }
  441. if(LsaTable->GetCallInfo(&CallInfo))
  442. {
  443. *pProcessID = CallInfo.ProcessId;
  444. return TRUE;
  445. }
  446. else
  447. {
  448. *pProcessID = (ULONG)-1;
  449. return FALSE;
  450. }
  451. }
  452. BOOL
  453. SslGetClientThread(ULONG *pThreadID)
  454. {
  455. SECPKG_CALL_INFO CallInfo;
  456. if(LsaTable == NULL)
  457. {
  458. *pThreadID = GetCurrentThreadId();
  459. return TRUE;
  460. }
  461. if(LsaTable->GetCallInfo(&CallInfo))
  462. {
  463. *pThreadID = CallInfo.ThreadId;
  464. return TRUE;
  465. }
  466. else
  467. {
  468. *pThreadID = (ULONG)-1;
  469. return FALSE;
  470. }
  471. }
  472. BOOL
  473. SslImpersonateClient(void)
  474. {
  475. SECPKG_CALL_INFO CallInfo;
  476. SECURITY_STATUS Status;
  477. // Don't impersonate if we're in the client process.
  478. if(LsaTable == NULL)
  479. {
  480. return FALSE;
  481. }
  482. // Don't impersonate if the client is running in the lsass process.
  483. if(LsaTable->GetCallInfo(&CallInfo))
  484. {
  485. if(CallInfo.ProcessId == GetCurrentProcessId())
  486. {
  487. // DebugLog((DEB_WARN, "Running locally, so don't impersonate.\n"));
  488. return FALSE;
  489. }
  490. }
  491. Status = LsaTable->ImpersonateClient();
  492. if(!NT_SUCCESS(Status))
  493. {
  494. SP_LOG_RESULT(Status);
  495. return FALSE;
  496. }
  497. return TRUE;
  498. }
  499. NTSTATUS
  500. SslGetClientLogonId(LUID *pLogonId)
  501. {
  502. SECPKG_CLIENT_INFO ClientInfo;
  503. SECURITY_STATUS Status;
  504. memset(pLogonId, 0, sizeof(LUID));
  505. Status = LsaTable->GetClientInfo(&ClientInfo);
  506. if(NT_SUCCESS(Status))
  507. {
  508. *pLogonId = ClientInfo.LogonId;
  509. }
  510. return Status;
  511. }
  512. PVOID SPExternalAlloc(DWORD cbLength)
  513. {
  514. if(LsaTable)
  515. {
  516. // Lsass process
  517. return LsaTable->AllocateLsaHeap(cbLength);
  518. }
  519. else
  520. {
  521. // Application process
  522. return LocalAlloc(LPTR, cbLength);
  523. }
  524. }
  525. VOID SPExternalFree(PVOID pMemory)
  526. {
  527. if(LsaTable)
  528. {
  529. // Lsass process
  530. LsaTable->FreeLsaHeap(pMemory);
  531. }
  532. else
  533. {
  534. // Application process
  535. LocalFree(pMemory);
  536. }
  537. }