2 * Copyright (c) 1997 - 2008 Kungliga Tekniska Högskolan
3 * (Royal Institute of Technology, Stockholm, Sweden).
6 * Redistribution and use in source and binary forms, with or without
7 * modification, are permitted provided that the following conditions
10 * 1. Redistributions of source code must retain the above copyright
11 * notice, this list of conditions and the following disclaimer.
13 * 2. Redistributions in binary form must reproduce the above copyright
14 * notice, this list of conditions and the following disclaimer in the
15 * documentation and/or other materials provided with the distribution.
17 * 3. Neither the name of the Institute nor the names of its contributors
18 * may be used to endorse or promote products derived from this software
19 * without specific prior written permission.
21 * THIS SOFTWARE IS PROVIDED BY THE INSTITUTE AND CONTRIBUTORS ``AS IS'' AND
22 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
23 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
24 * ARE DISCLAIMED. IN NO EVENT SHALL THE INSTITUTE OR CONTRIBUTORS BE LIABLE
25 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
26 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
27 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
28 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
29 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
30 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
34 #include "krb5_locl.h"
36 /* coverity[+alloc : arg-*3] */
37 KRB5_LIB_FUNCTION krb5_error_code KRB5_LIB_CALL
38 krb5_salttype_to_string (krb5_context context
,
43 struct _krb5_encryption_type
*e
;
46 e
= _krb5_find_enctype (etype
);
48 krb5_set_error_message(context
, KRB5_PROG_ETYPE_NOSUPP
,
49 "encryption type %d not supported",
51 return KRB5_PROG_ETYPE_NOSUPP
;
53 for (st
= e
->keytype
->string_to_key
; st
&& st
->type
; st
++) {
54 if (st
->type
== stype
) {
55 *string
= strdup (st
->name
);
57 return krb5_enomem(context
);
61 krb5_set_error_message (context
, HEIM_ERR_SALTTYPE_NOSUPP
,
62 "salttype %d not supported", stype
);
63 return HEIM_ERR_SALTTYPE_NOSUPP
;
66 KRB5_LIB_FUNCTION krb5_error_code KRB5_LIB_CALL
67 krb5_string_to_salttype (krb5_context context
,
70 krb5_salttype
*salttype
)
72 struct _krb5_encryption_type
*e
;
75 e
= _krb5_find_enctype (etype
);
77 krb5_set_error_message(context
, KRB5_PROG_ETYPE_NOSUPP
,
78 N_("encryption type %d not supported", ""),
80 return KRB5_PROG_ETYPE_NOSUPP
;
82 for (st
= e
->keytype
->string_to_key
; st
&& st
->type
; st
++) {
83 if (strcasecmp (st
->name
, string
) == 0) {
88 krb5_set_error_message(context
, HEIM_ERR_SALTTYPE_NOSUPP
,
89 N_("salttype %s not supported", ""), string
);
90 return HEIM_ERR_SALTTYPE_NOSUPP
;
93 KRB5_LIB_FUNCTION krb5_error_code KRB5_LIB_CALL
94 krb5_get_pw_salt(krb5_context context
,
95 krb5_const_principal principal
,
103 salt
->salttype
= KRB5_PW_SALT
;
104 len
= strlen(principal
->realm
);
105 for (i
= 0; i
< principal
->name
.name_string
.len
; ++i
)
106 len
+= strlen(principal
->name
.name_string
.val
[i
]);
107 ret
= krb5_data_alloc (&salt
->saltvalue
, len
);
110 p
= salt
->saltvalue
.data
;
111 memcpy (p
, principal
->realm
, strlen(principal
->realm
));
112 p
+= strlen(principal
->realm
);
113 for (i
= 0; i
< principal
->name
.name_string
.len
; ++i
) {
115 principal
->name
.name_string
.val
[i
],
116 strlen(principal
->name
.name_string
.val
[i
]));
117 p
+= strlen(principal
->name
.name_string
.val
[i
]);
122 KRB5_LIB_FUNCTION krb5_error_code KRB5_LIB_CALL
123 krb5_free_salt(krb5_context context
,
126 krb5_data_free(&salt
.saltvalue
);
130 KRB5_LIB_FUNCTION krb5_error_code KRB5_LIB_CALL
131 krb5_string_to_key_data (krb5_context context
,
132 krb5_enctype enctype
,
134 krb5_principal principal
,
140 ret
= krb5_get_pw_salt(context
, principal
, &salt
);
143 ret
= krb5_string_to_key_data_salt(context
, enctype
, password
, salt
, key
);
144 krb5_free_salt(context
, salt
);
148 KRB5_LIB_FUNCTION krb5_error_code KRB5_LIB_CALL
149 krb5_string_to_key (krb5_context context
,
150 krb5_enctype enctype
,
151 const char *password
,
152 krb5_principal principal
,
156 pw
.data
= rk_UNCONST(password
);
157 pw
.length
= strlen(password
);
158 return krb5_string_to_key_data(context
, enctype
, pw
, principal
, key
);
161 KRB5_LIB_FUNCTION krb5_error_code KRB5_LIB_CALL
162 krb5_string_to_key_data_salt (krb5_context context
,
163 krb5_enctype enctype
,
169 krb5_data_zero(&opaque
);
170 return krb5_string_to_key_data_salt_opaque(context
, enctype
, password
,
175 * Do a string -> key for encryption type `enctype' operation on
176 * `password' (with salt `salt' and the enctype specific data string
177 * `opaque'), returning the resulting key in `key'
180 KRB5_LIB_FUNCTION krb5_error_code KRB5_LIB_CALL
181 krb5_string_to_key_data_salt_opaque (krb5_context context
,
182 krb5_enctype enctype
,
188 struct _krb5_encryption_type
*et
=_krb5_find_enctype(enctype
);
189 struct salt_type
*st
;
191 krb5_set_error_message(context
, KRB5_PROG_ETYPE_NOSUPP
,
192 N_("encryption type %d not supported", ""),
194 return KRB5_PROG_ETYPE_NOSUPP
;
196 for(st
= et
->keytype
->string_to_key
; st
&& st
->type
; st
++)
197 if(st
->type
== salt
.salttype
)
198 return (*st
->string_to_key
)(context
, enctype
, password
,
200 krb5_set_error_message(context
, HEIM_ERR_SALTTYPE_NOSUPP
,
201 N_("salt type %d not supported", ""),
203 return HEIM_ERR_SALTTYPE_NOSUPP
;
207 * Do a string -> key for encryption type `enctype' operation on the
208 * string `password' (with salt `salt'), returning the resulting key
212 KRB5_LIB_FUNCTION krb5_error_code KRB5_LIB_CALL
213 krb5_string_to_key_salt (krb5_context context
,
214 krb5_enctype enctype
,
215 const char *password
,
220 pw
.data
= rk_UNCONST(password
);
221 pw
.length
= strlen(password
);
222 return krb5_string_to_key_data_salt(context
, enctype
, pw
, salt
, key
);
225 KRB5_LIB_FUNCTION krb5_error_code KRB5_LIB_CALL
226 krb5_string_to_key_salt_opaque (krb5_context context
,
227 krb5_enctype enctype
,
228 const char *password
,
234 pw
.data
= rk_UNCONST(password
);
235 pw
.length
= strlen(password
);
236 return krb5_string_to_key_data_salt_opaque(context
, enctype
,
237 pw
, salt
, opaque
, key
);
241 KRB5_LIB_FUNCTION krb5_error_code KRB5_LIB_CALL
242 krb5_string_to_key_derived(krb5_context context
,
248 struct _krb5_encryption_type
*et
= _krb5_find_enctype(etype
);
250 struct _krb5_key_data kd
;
255 krb5_set_error_message (context
, KRB5_PROG_ETYPE_NOSUPP
,
256 N_("encryption type %d not supported", ""),
258 return KRB5_PROG_ETYPE_NOSUPP
;
260 keylen
= et
->keytype
->bits
/ 8;
264 return krb5_enomem(context
);
265 ret
= krb5_data_alloc(&kd
.key
->keyvalue
, et
->keytype
->size
);
270 kd
.key
->keytype
= etype
;
271 tmp
= malloc (keylen
);
273 krb5_free_keyblock(context
, kd
.key
);
274 return krb5_enomem(context
);
276 ret
= _krb5_n_fold(str
, len
, tmp
, keylen
);
279 krb5_enomem(context
);
283 _krb5_DES3_random_to_key(context
, kd
.key
, tmp
, keylen
);
284 memset(tmp
, 0, keylen
);
286 ret
= _krb5_derive_key(context
,
289 "kerberos", /* XXX well known constant */
292 _krb5_free_key_data(context
, &kd
, et
);
295 ret
= krb5_copy_keyblock_contents(context
, kd
.key
, key
);
296 _krb5_free_key_data(context
, &kd
, et
);