1 /**
2 * WinPR: Windows Portable Runtime
3 * Credential Security Support Provider (CredSSP)
4 *
5 * Copyright 2010-2014 Marc-Andre Moreau <marcandre.moreau@gmail.com>
6 *
7 * Licensed under the Apache License, Version 2.0 (the "License");
8 * you may not use this file except in compliance with the License.
9 * You may obtain a copy of the License at
10 *
11 * http://www.apache.org/licenses/LICENSE-2.0
12 *
13 * Unless required by applicable law or agreed to in writing, software
14 * distributed under the License is distributed on an "AS IS" BASIS,
15 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
16 * See the License for the specific language governing permissions and
17 * limitations under the License.
18 */
19
20 #ifdef HAVE_CONFIG_H
21 #include "config.h"
22 #endif
23
24 #include <winpr/crt.h>
25 #include <winpr/sspi.h>
26
27 #include "credssp.h"
28
29 #include "../sspi.h"
30 #include "../log.h"
31
32 #define TAG WINPR_TAG("sspi.CredSSP")
33
34 static const char* CREDSSP_PACKAGE_NAME = "CredSSP";
35
credssp_InitializeSecurityContextW(PCredHandle phCredential,PCtxtHandle phContext,SEC_WCHAR * pszTargetName,ULONG fContextReq,ULONG Reserved1,ULONG TargetDataRep,PSecBufferDesc pInput,ULONG Reserved2,PCtxtHandle phNewContext,PSecBufferDesc pOutput,PULONG pfContextAttr,PTimeStamp ptsExpiry)36 static SECURITY_STATUS SEC_ENTRY credssp_InitializeSecurityContextW(
37 PCredHandle phCredential, PCtxtHandle phContext, SEC_WCHAR* pszTargetName, ULONG fContextReq,
38 ULONG Reserved1, ULONG TargetDataRep, PSecBufferDesc pInput, ULONG Reserved2,
39 PCtxtHandle phNewContext, PSecBufferDesc pOutput, PULONG pfContextAttr, PTimeStamp ptsExpiry)
40 {
41 WLog_ERR(TAG, "[%s]: TODO: Implement", __FUNCTION__);
42 return SEC_E_UNSUPPORTED_FUNCTION;
43 }
44
credssp_InitializeSecurityContextA(PCredHandle phCredential,PCtxtHandle phContext,SEC_CHAR * pszTargetName,ULONG fContextReq,ULONG Reserved1,ULONG TargetDataRep,PSecBufferDesc pInput,ULONG Reserved2,PCtxtHandle phNewContext,PSecBufferDesc pOutput,PULONG pfContextAttr,PTimeStamp ptsExpiry)45 static SECURITY_STATUS SEC_ENTRY credssp_InitializeSecurityContextA(
46 PCredHandle phCredential, PCtxtHandle phContext, SEC_CHAR* pszTargetName, ULONG fContextReq,
47 ULONG Reserved1, ULONG TargetDataRep, PSecBufferDesc pInput, ULONG Reserved2,
48 PCtxtHandle phNewContext, PSecBufferDesc pOutput, PULONG pfContextAttr, PTimeStamp ptsExpiry)
49 {
50 CREDSSP_CONTEXT* context;
51 SSPI_CREDENTIALS* credentials;
52 context = (CREDSSP_CONTEXT*)sspi_SecureHandleGetLowerPointer(phContext);
53
54 if (!context)
55 {
56 context = credssp_ContextNew();
57
58 if (!context)
59 return SEC_E_INSUFFICIENT_MEMORY;
60
61 credentials = (SSPI_CREDENTIALS*)sspi_SecureHandleGetLowerPointer(phCredential);
62
63 if (!credentials)
64 {
65 credssp_ContextFree(context);
66 return SEC_E_INVALID_HANDLE;
67 }
68
69 sspi_SecureHandleSetLowerPointer(phNewContext, context);
70 sspi_SecureHandleSetUpperPointer(phNewContext, (void*)CREDSSP_PACKAGE_NAME);
71 }
72
73 return SEC_E_OK;
74 }
75
credssp_ContextNew(void)76 CREDSSP_CONTEXT* credssp_ContextNew(void)
77 {
78 CREDSSP_CONTEXT* context;
79 context = (CREDSSP_CONTEXT*)calloc(1, sizeof(CREDSSP_CONTEXT));
80
81 if (!context)
82 return NULL;
83
84 return context;
85 }
86
credssp_ContextFree(CREDSSP_CONTEXT * context)87 void credssp_ContextFree(CREDSSP_CONTEXT* context)
88 {
89 free(context);
90 }
91
credssp_QueryContextAttributes(PCtxtHandle phContext,ULONG ulAttribute,void * pBuffer)92 static SECURITY_STATUS SEC_ENTRY credssp_QueryContextAttributes(PCtxtHandle phContext,
93 ULONG ulAttribute, void* pBuffer)
94 {
95 if (!phContext)
96 return SEC_E_INVALID_HANDLE;
97
98 if (!pBuffer)
99 return SEC_E_INSUFFICIENT_MEMORY;
100
101 WLog_ERR(TAG, "[%s]: TODO: Implement", __FUNCTION__);
102 return SEC_E_UNSUPPORTED_FUNCTION;
103 }
104
credssp_AcquireCredentialsHandleW(SEC_WCHAR * pszPrincipal,SEC_WCHAR * pszPackage,ULONG fCredentialUse,void * pvLogonID,void * pAuthData,SEC_GET_KEY_FN pGetKeyFn,void * pvGetKeyArgument,PCredHandle phCredential,PTimeStamp ptsExpiry)105 static SECURITY_STATUS SEC_ENTRY credssp_AcquireCredentialsHandleW(
106 SEC_WCHAR* pszPrincipal, SEC_WCHAR* pszPackage, ULONG fCredentialUse, void* pvLogonID,
107 void* pAuthData, SEC_GET_KEY_FN pGetKeyFn, void* pvGetKeyArgument, PCredHandle phCredential,
108 PTimeStamp ptsExpiry)
109 {
110 WLog_ERR(TAG, "[%s]: TODO: Implement", __FUNCTION__);
111 return SEC_E_UNSUPPORTED_FUNCTION;
112 }
113
credssp_AcquireCredentialsHandleA(SEC_CHAR * pszPrincipal,SEC_CHAR * pszPackage,ULONG fCredentialUse,void * pvLogonID,void * pAuthData,SEC_GET_KEY_FN pGetKeyFn,void * pvGetKeyArgument,PCredHandle phCredential,PTimeStamp ptsExpiry)114 static SECURITY_STATUS SEC_ENTRY credssp_AcquireCredentialsHandleA(
115 SEC_CHAR* pszPrincipal, SEC_CHAR* pszPackage, ULONG fCredentialUse, void* pvLogonID,
116 void* pAuthData, SEC_GET_KEY_FN pGetKeyFn, void* pvGetKeyArgument, PCredHandle phCredential,
117 PTimeStamp ptsExpiry)
118 {
119 SSPI_CREDENTIALS* credentials;
120 SEC_WINNT_AUTH_IDENTITY* identity;
121
122 if (fCredentialUse == SECPKG_CRED_OUTBOUND)
123 {
124 credentials = sspi_CredentialsNew();
125
126 if (!credentials)
127 return SEC_E_INSUFFICIENT_MEMORY;
128
129 identity = (SEC_WINNT_AUTH_IDENTITY*)pAuthData;
130 CopyMemory(&(credentials->identity), identity, sizeof(SEC_WINNT_AUTH_IDENTITY));
131 sspi_SecureHandleSetLowerPointer(phCredential, (void*)credentials);
132 sspi_SecureHandleSetUpperPointer(phCredential, (void*)CREDSSP_PACKAGE_NAME);
133 return SEC_E_OK;
134 }
135
136 WLog_ERR(TAG, "[%s]: TODO: Implement", __FUNCTION__);
137 return SEC_E_UNSUPPORTED_FUNCTION;
138 }
139
credssp_QueryCredentialsAttributesW(PCredHandle phCredential,ULONG ulAttribute,void * pBuffer)140 static SECURITY_STATUS SEC_ENTRY credssp_QueryCredentialsAttributesW(PCredHandle phCredential,
141 ULONG ulAttribute,
142 void* pBuffer)
143 {
144 WLog_ERR(TAG, "[%s]: TODO: Implement", __FUNCTION__);
145 return SEC_E_UNSUPPORTED_FUNCTION;
146 }
147
credssp_QueryCredentialsAttributesA(PCredHandle phCredential,ULONG ulAttribute,void * pBuffer)148 static SECURITY_STATUS SEC_ENTRY credssp_QueryCredentialsAttributesA(PCredHandle phCredential,
149 ULONG ulAttribute,
150 void* pBuffer)
151 {
152 if (ulAttribute == SECPKG_CRED_ATTR_NAMES)
153 {
154 SSPI_CREDENTIALS* credentials =
155 (SSPI_CREDENTIALS*)sspi_SecureHandleGetLowerPointer(phCredential);
156
157 if (!credentials)
158 return SEC_E_INVALID_HANDLE;
159
160 return SEC_E_OK;
161 }
162
163 WLog_ERR(TAG, "[%s]: TODO: Implement", __FUNCTION__);
164 return SEC_E_UNSUPPORTED_FUNCTION;
165 }
166
credssp_FreeCredentialsHandle(PCredHandle phCredential)167 static SECURITY_STATUS SEC_ENTRY credssp_FreeCredentialsHandle(PCredHandle phCredential)
168 {
169 SSPI_CREDENTIALS* credentials;
170
171 if (!phCredential)
172 return SEC_E_INVALID_HANDLE;
173
174 credentials = (SSPI_CREDENTIALS*)sspi_SecureHandleGetLowerPointer(phCredential);
175
176 if (!credentials)
177 return SEC_E_INVALID_HANDLE;
178
179 sspi_CredentialsFree(credentials);
180 return SEC_E_OK;
181 }
182
credssp_EncryptMessage(PCtxtHandle phContext,ULONG fQOP,PSecBufferDesc pMessage,ULONG MessageSeqNo)183 static SECURITY_STATUS SEC_ENTRY credssp_EncryptMessage(PCtxtHandle phContext, ULONG fQOP,
184 PSecBufferDesc pMessage, ULONG MessageSeqNo)
185 {
186 WLog_ERR(TAG, "[%s]: TODO: Implement", __FUNCTION__);
187 return SEC_E_UNSUPPORTED_FUNCTION;
188 }
189
credssp_DecryptMessage(PCtxtHandle phContext,PSecBufferDesc pMessage,ULONG MessageSeqNo,ULONG * pfQOP)190 static SECURITY_STATUS SEC_ENTRY credssp_DecryptMessage(PCtxtHandle phContext,
191 PSecBufferDesc pMessage, ULONG MessageSeqNo,
192 ULONG* pfQOP)
193 {
194 WLog_ERR(TAG, "[%s]: TODO: Implement", __FUNCTION__);
195 return SEC_E_UNSUPPORTED_FUNCTION;
196 }
197
credssp_MakeSignature(PCtxtHandle phContext,ULONG fQOP,PSecBufferDesc pMessage,ULONG MessageSeqNo)198 static SECURITY_STATUS SEC_ENTRY credssp_MakeSignature(PCtxtHandle phContext, ULONG fQOP,
199 PSecBufferDesc pMessage, ULONG MessageSeqNo)
200 {
201 WLog_ERR(TAG, "[%s]: TODO: Implement", __FUNCTION__);
202 return SEC_E_UNSUPPORTED_FUNCTION;
203 }
204
credssp_VerifySignature(PCtxtHandle phContext,PSecBufferDesc pMessage,ULONG MessageSeqNo,ULONG * pfQOP)205 static SECURITY_STATUS SEC_ENTRY credssp_VerifySignature(PCtxtHandle phContext,
206 PSecBufferDesc pMessage,
207 ULONG MessageSeqNo, ULONG* pfQOP)
208 {
209 WLog_ERR(TAG, "[%s]: TODO: Implement", __FUNCTION__);
210 return SEC_E_UNSUPPORTED_FUNCTION;
211 }
212
213 const SecurityFunctionTableA CREDSSP_SecurityFunctionTableA = {
214 1, /* dwVersion */
215 NULL, /* EnumerateSecurityPackages */
216 credssp_QueryCredentialsAttributesA, /* QueryCredentialsAttributes */
217 credssp_AcquireCredentialsHandleA, /* AcquireCredentialsHandle */
218 credssp_FreeCredentialsHandle, /* FreeCredentialsHandle */
219 NULL, /* Reserved2 */
220 credssp_InitializeSecurityContextA, /* InitializeSecurityContext */
221 NULL, /* AcceptSecurityContext */
222 NULL, /* CompleteAuthToken */
223 NULL, /* DeleteSecurityContext */
224 NULL, /* ApplyControlToken */
225 credssp_QueryContextAttributes, /* QueryContextAttributes */
226 NULL, /* ImpersonateSecurityContext */
227 NULL, /* RevertSecurityContext */
228 credssp_MakeSignature, /* MakeSignature */
229 credssp_VerifySignature, /* VerifySignature */
230 NULL, /* FreeContextBuffer */
231 NULL, /* QuerySecurityPackageInfo */
232 NULL, /* Reserved3 */
233 NULL, /* Reserved4 */
234 NULL, /* ExportSecurityContext */
235 NULL, /* ImportSecurityContext */
236 NULL, /* AddCredentials */
237 NULL, /* Reserved8 */
238 NULL, /* QuerySecurityContextToken */
239 credssp_EncryptMessage, /* EncryptMessage */
240 credssp_DecryptMessage, /* DecryptMessage */
241 NULL, /* SetContextAttributes */
242 };
243
244 const SecurityFunctionTableW CREDSSP_SecurityFunctionTableW = {
245 1, /* dwVersion */
246 NULL, /* EnumerateSecurityPackages */
247 credssp_QueryCredentialsAttributesW, /* QueryCredentialsAttributes */
248 credssp_AcquireCredentialsHandleW, /* AcquireCredentialsHandle */
249 credssp_FreeCredentialsHandle, /* FreeCredentialsHandle */
250 NULL, /* Reserved2 */
251 credssp_InitializeSecurityContextW, /* InitializeSecurityContext */
252 NULL, /* AcceptSecurityContext */
253 NULL, /* CompleteAuthToken */
254 NULL, /* DeleteSecurityContext */
255 NULL, /* ApplyControlToken */
256 credssp_QueryContextAttributes, /* QueryContextAttributes */
257 NULL, /* ImpersonateSecurityContext */
258 NULL, /* RevertSecurityContext */
259 credssp_MakeSignature, /* MakeSignature */
260 credssp_VerifySignature, /* VerifySignature */
261 NULL, /* FreeContextBuffer */
262 NULL, /* QuerySecurityPackageInfo */
263 NULL, /* Reserved3 */
264 NULL, /* Reserved4 */
265 NULL, /* ExportSecurityContext */
266 NULL, /* ImportSecurityContext */
267 NULL, /* AddCredentials */
268 NULL, /* Reserved8 */
269 NULL, /* QuerySecurityContextToken */
270 credssp_EncryptMessage, /* EncryptMessage */
271 credssp_DecryptMessage, /* DecryptMessage */
272 NULL, /* SetContextAttributes */
273 };
274
275 const SecPkgInfoA CREDSSP_SecPkgInfoA = {
276 0x000110733, /* fCapabilities */
277 1, /* wVersion */
278 0xFFFF, /* wRPCID */
279 0x000090A8, /* cbMaxToken */
280 "CREDSSP", /* Name */
281 "Microsoft CredSSP Security Provider" /* Comment */
282 };
283
284 static WCHAR CREDSSP_SecPkgInfoW_Name[] = { 'C', 'R', 'E', 'D', 'S', 'S', 'P', '\0' };
285
286 static WCHAR CREDSSP_SecPkgInfoW_Comment[] = { 'M', 'i', 'c', 'r', 'o', 's', 'o', 'f', 't',
287 ' ', 'C', 'r', 'e', 'd', 'S', 'S', 'P', ' ',
288 'S', 'e', 'c', 'u', 'r', 'i', 't', 'y', ' ',
289 'P', 'r', 'o', 'v', 'i', 'd', 'e', 'r', '\0' };
290
291 const SecPkgInfoW CREDSSP_SecPkgInfoW = {
292 0x000110733, /* fCapabilities */
293 1, /* wVersion */
294 0xFFFF, /* wRPCID */
295 0x000090A8, /* cbMaxToken */
296 CREDSSP_SecPkgInfoW_Name, /* Name */
297 CREDSSP_SecPkgInfoW_Comment /* Comment */
298 };
299