1 Index: lib/gssapi/ntlm/crypto.c
2 ===================================================================
3 --- lib/gssapi/ntlm/crypto.c (revision 796)
4 +++ lib/gssapi/ntlm/crypto.c (working copy)
7 * Copyright (c) 2006 Kungliga Tekniska Högskolan
8 * (Royal Institute of Technology, Stockholm, Sweden).
9 + * Copyright (c) 2008 Red Hat Inc.
10 * All rights reserved.
12 * Redistribution and use in source and binary forms, with or without
14 v2_seal_message(const gss_buffer_t in,
15 unsigned char signkey[16],
17 + RC4_KEY *signsealkey,
22 + unsigned char sealed_sig[16];
25 if (in->length + 16 < in->length)
30 - RC4(sealkey, in->length, in->value, p);
32 - ret = v2_sign_message(in, signkey, sealkey, seq, &p[in->length]);
33 + /* Must encrypt signature after encrypting the data, so don't specify signseal key here */
34 + ret = v2_sign_message(in, signkey, NULL, seq, &p[in->length]);
40 + RC4(sealkey, in->length, in->value, p);
42 + /* Instead deal with it here */
44 + RC4(sealkey, 16, &p[in->length], sealed_sig);
45 + memcpy(&p[in->length], sealed_sig, 16);
49 out->length = in->length + 16;
52 v2_unseal_message(gss_buffer_t in,
53 unsigned char signkey[16],
55 + RC4_KEY *signsealkey,
61 RC4(sealkey, out->length, in->value, out->value);
63 - ret = v2_verify_message(out, signkey, sealkey, seq,
64 + ret = v2_verify_message(out, signkey, signsealkey, seq,
65 ((const unsigned char *)in->value) + out->length);
73 +v2_seal_message_ex(const gss_buffer_t in_to_sign,
74 + const gss_buffer_t in_to_seal,
75 + unsigned char signkey[16],
77 + RC4_KEY *signsealkey,
79 + gss_buffer_t out_signature,
80 + gss_buffer_t out_sealed)
83 + unsigned char sealed_sig[16];
86 + out_sealed->value = malloc(in_to_seal->length);
87 + if (out_sealed->value == NULL)
90 + out_signature->value = malloc(16);
91 + if (out_signature->value == NULL) {
92 + free(out_sealed->value);
96 + /* Must encrypt signature after encrypting the data, so don't specify signseal key here */
97 + ret = v2_sign_message(in_to_sign, signkey, NULL, seq, out_signature->value);
103 + out_signature->length = 16;
105 + RC4(sealkey, in_to_seal->length, in_to_seal->value, out_sealed->value);
107 + out_sealed->length = in_to_sign->length;
109 + /* Instead deal with it here */
111 + RC4(sealkey, 16, out_signature->value, sealed_sig);
112 + memcpy(out_signature->value, sealed_sig, 16);
119 +v2_unseal_message_ex(gss_buffer_t in_signed,
120 + gss_buffer_t in_sealed,
121 + gss_buffer_t in_signature,
122 + unsigned char signkey[16],
124 + RC4_KEY *signsealkey,
126 + gss_buffer_t out_unsealed)
129 + gss_buffer_desc unsealed_with_aead;
131 + if (in_sealed->value < in_signed->value) {
132 + return GSS_S_BAD_MIC;
135 + if (&((char *)in_sealed->value)[in_sealed->length] > &((char *)in_signed->value)[in_signed->length]) {
136 + return GSS_S_BAD_MIC;
139 + if (in_signature->length < 16)
140 + return GSS_S_BAD_MIC;
142 + unsealed_with_aead.value = malloc(in_signed->length);
143 + if (unsealed_with_aead.value == NULL)
146 + out_unsealed->length = in_sealed->length;
147 + out_unsealed->value = malloc(out_unsealed->length);
148 + if (out_unsealed->value == NULL) {
149 + free(unsealed_with_aead.value);
150 + return GSS_S_BAD_MIC;
153 + RC4(sealkey, out_unsealed->length, in_sealed->value, out_unsealed->value);
155 + memcpy(unsealed_with_aead.value, in_signed->value, in_signed->length);
157 + /* Someone please check this is doing the right thing... */
158 + memcpy(&((char *)unsealed_with_aead.value)[(char *)in_sealed->value - (char *)in_signed->value],
159 + out_unsealed->value, out_unsealed->length);
161 + ret = v2_verify_message(&unsealed_with_aead, signkey, sealkey, seq, in_signature->value);
164 + gss_release_buffer(&junk, out_unsealed);
173 return v2_seal_message(input_message_buffer,
174 ctx->u.v2.send.signkey,
175 ctx->u.v2.send.seq++,
176 + ctx->u.v2.send.signsealkey,
177 &ctx->u.v2.send.sealkey,
178 output_message_buffer);
181 return v2_unseal_message(input_message_buffer,
182 ctx->u.v2.recv.signkey,
183 ctx->u.v2.recv.seq++,
184 + ctx->u.v2.send.signsealkey,
185 &ctx->u.v2.recv.sealkey,
186 output_message_buffer);
188 @@ -593,3 +703,134 @@
190 return GSS_S_UNAVAILABLE;
196 +OM_uint32 _gss_ntlm_wrap_ex
197 +(OM_uint32 * minor_status,
198 + const gss_ctx_id_t context_handle,
201 + const gss_buffer_t associated_data_buffer,
202 + const gss_buffer_t input_message_buffer,
204 + gss_buffer_t output_token_buffer,
205 + gss_buffer_t output_message_buffer
208 + ntlm_ctx ctx = (ntlm_ctx)context_handle;
215 + if (output_message_buffer == GSS_C_NO_BUFFER)
216 + return GSS_S_FAILURE;
219 + if (CTX_FLAGS_ISSET(ctx, NTLM_NEG_SEAL|NTLM_NEG_NTLM2_SESSION)) {
221 + return v2_seal_message_ex(associated_data_buffer,
222 + input_message_buffer,
223 + ctx->u.v2.send.signkey,
224 + ctx->u.v2.send.seq++,
225 + ctx->u.v2.send.signsealkey,
226 + &ctx->u.v2.send.sealkey,
227 + output_token_buffer,
228 + output_message_buffer);
230 + } else if (CTX_FLAGS_ISSET(ctx, NTLM_NEG_SEAL)) {
233 + output_message_buffer->length = input_message_buffer->length;
234 + output_message_buffer->value = malloc(output_message_buffer->length);
235 + if (output_message_buffer->value == NULL) {
236 + output_message_buffer->length = 0;
237 + return GSS_S_FAILURE;
241 + RC4(&ctx->u.v1.crypto_send.key, input_message_buffer->length,
242 + input_message_buffer->value, output_message_buffer->value);
244 + ret = _gss_ntlm_get_mic(minor_status, context_handle,
245 + 0, input_message_buffer,
246 + output_token_buffer);
248 + gss_release_buffer(&junk, output_message_buffer);
251 + return GSS_S_COMPLETE;
254 + return GSS_S_UNAVAILABLE;
261 +OM_uint32 _gss_ntlm_unwrap_ex
262 +(OM_uint32 * minor_status,
263 + const gss_ctx_id_t context_handle,
264 + const gss_buffer_t token_header_buffer,
265 + const gss_buffer_t associated_data_buffer,
266 + const gss_buffer_t input_message_buffer,
267 + gss_buffer_t output_message_buffer,
269 + gss_qop_t * qop_state
272 + ntlm_ctx ctx = (ntlm_ctx)context_handle;
277 + if (output_message_buffer) {
278 + output_message_buffer->value = NULL;
279 + output_message_buffer->length = 0;
286 + if (CTX_FLAGS_ISSET(ctx, NTLM_NEG_SEAL|NTLM_NEG_NTLM2_SESSION)) {
288 + return v2_unseal_message_ex(associated_data_buffer,
289 + input_message_buffer,
290 + token_header_buffer,
291 + ctx->u.v2.recv.signkey,
292 + ctx->u.v2.recv.seq++,
293 + ctx->u.v2.recv.signsealkey,
294 + &ctx->u.v2.recv.sealkey,
295 + output_message_buffer);
297 + } else if (CTX_FLAGS_ISSET(ctx, NTLM_NEG_SEAL)) {
300 + output_message_buffer->length = input_message_buffer->length;
301 + output_message_buffer->value = malloc(output_message_buffer->length);
302 + if (output_message_buffer->value == NULL) {
303 + output_message_buffer->length = 0;
304 + return GSS_S_FAILURE;
307 + RC4(&ctx->u.v1.crypto_recv.key, output_message_buffer->length,
308 + input_message_buffer->value, output_message_buffer->value);
310 + ret = _gss_ntlm_verify_mic(minor_status, context_handle,
311 + output_message_buffer,
312 + token_header_buffer, NULL);
314 + gss_release_buffer(&junk, output_message_buffer);
318 + return GSS_S_COMPLETE;
321 + return GSS_S_UNAVAILABLE;
323 Index: lib/gssapi/ntlm/external.c
324 ===================================================================
325 --- lib/gssapi/ntlm/external.c (revision 796)
326 +++ lib/gssapi/ntlm/external.c (working copy)
328 _gss_ntlm_verify_mic,
332 + _gss_ntlm_unwrap_ex,
333 _gss_ntlm_display_status,
335 _gss_ntlm_compare_name,