1 /* 2 * Copyright (c) 1997, 1998, 1999 Kungliga Tekniska H�gskolan 3 * (Royal Institute of Technology, Stockholm, Sweden). 4 * All rights reserved. 5 * 6 * Redistribution and use in source and binary forms, with or without 7 * modification, are permitted provided that the following conditions 8 * are met: 9 * 10 * 1. Redistributions of source code must retain the above copyright 11 * notice, this list of conditions and the following disclaimer. 12 * 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. 16 * 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. 20 * 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 31 * SUCH DAMAGE. 32 */ 33 34 #include "krb5_locl.h" 35 36 RCSID("$Id: auth_context.c,v 1.50 1999/12/02 17:05:07 joda Exp $"); 37 38 krb5_error_code 39 krb5_auth_con_init(krb5_context context, 40 krb5_auth_context *auth_context) 41 { 42 krb5_auth_context p; 43 44 ALLOC(p, 1); 45 if(!p) 46 return ENOMEM; 47 memset(p, 0, sizeof(*p)); 48 ALLOC(p->authenticator, 1); 49 if (!p->authenticator) { 50 free(p); 51 return ENOMEM; 52 } 53 memset (p->authenticator, 0, sizeof(*p->authenticator)); 54 p->flags = KRB5_AUTH_CONTEXT_DO_TIME; 55 56 p->local_address = NULL; 57 p->remote_address = NULL; 58 p->local_port = 0; 59 p->remote_port = 0; 60 p->keytype = KEYTYPE_NULL; 61 p->cksumtype = CKSUMTYPE_NONE; 62 *auth_context = p; 63 return 0; 64 } 65 66 krb5_error_code 67 krb5_auth_con_free(krb5_context context, 68 krb5_auth_context auth_context) 69 { 70 krb5_free_authenticator(context, &auth_context->authenticator); 71 if(auth_context->local_address){ 72 free_HostAddress(auth_context->local_address); 73 free(auth_context->local_address); 74 } 75 if(auth_context->remote_address){ 76 free_HostAddress(auth_context->remote_address); 77 free(auth_context->remote_address); 78 } 79 if(auth_context->keyblock) 80 krb5_free_keyblock(context, auth_context->keyblock); 81 krb5_free_keyblock(context, auth_context->remote_subkey); 82 krb5_free_keyblock(context, auth_context->local_subkey); 83 free (auth_context); 84 return 0; 85 } 86 87 krb5_error_code 88 krb5_auth_con_setflags(krb5_context context, 89 krb5_auth_context auth_context, 90 int32_t flags) 91 { 92 auth_context->flags = flags; 93 return 0; 94 } 95 96 97 krb5_error_code 98 krb5_auth_con_getflags(krb5_context context, 99 krb5_auth_context auth_context, 100 int32_t *flags) 101 { 102 *flags = auth_context->flags; 103 return 0; 104 } 105 106 107 krb5_error_code 108 krb5_auth_con_setaddrs(krb5_context context, 109 krb5_auth_context auth_context, 110 krb5_address *local_addr, 111 krb5_address *remote_addr) 112 { 113 if (local_addr) { 114 if (auth_context->local_address) 115 krb5_free_address (context, auth_context->local_address); 116 else 117 auth_context->local_address = malloc(sizeof(krb5_address)); 118 krb5_copy_address(context, local_addr, auth_context->local_address); 119 } 120 if (remote_addr) { 121 if (auth_context->remote_address) 122 krb5_free_address (context, auth_context->remote_address); 123 else 124 auth_context->remote_address = malloc(sizeof(krb5_address)); 125 krb5_copy_address(context, remote_addr, auth_context->remote_address); 126 } 127 return 0; 128 } 129 130 krb5_error_code 131 krb5_auth_con_setaddrs_from_fd (krb5_context context, 132 krb5_auth_context auth_context, 133 void *p_fd) 134 { 135 int fd = *((int *)p_fd); 136 krb5_error_code ret; 137 krb5_address local_k_address, remote_k_address; 138 krb5_address *lptr = NULL, *rptr = NULL; 139 struct sockaddr_storage ss_local, ss_remote; 140 struct sockaddr *local = (struct sockaddr *)&ss_local; 141 struct sockaddr *remote = (struct sockaddr *)&ss_remote; 142 int len; 143 144 if (auth_context->local_address == NULL) { 145 len = sizeof(ss_local); 146 if(getsockname(fd, local, &len) < 0) { 147 ret = errno; 148 goto out; 149 } 150 krb5_sockaddr2address (local, &local_k_address); 151 krb5_sockaddr2port (local, &auth_context->local_port); 152 lptr = &local_k_address; 153 } 154 if (auth_context->remote_address == NULL) { 155 len = sizeof(ss_remote); 156 if(getpeername(fd, remote, &len) < 0) { 157 ret = errno; 158 goto out; 159 } 160 krb5_sockaddr2address (remote, &remote_k_address); 161 krb5_sockaddr2port (remote, &auth_context->remote_port); 162 rptr = &remote_k_address; 163 } 164 ret = krb5_auth_con_setaddrs (context, 165 auth_context, 166 lptr, 167 rptr); 168 out: 169 if (lptr) 170 krb5_free_address (context, lptr); 171 if (rptr) 172 krb5_free_address (context, rptr); 173 return ret; 174 } 175 176 krb5_error_code 177 krb5_auth_con_getaddrs(krb5_context context, 178 krb5_auth_context auth_context, 179 krb5_address **local_addr, 180 krb5_address **remote_addr) 181 { 182 if(*local_addr) 183 krb5_free_address (context, *local_addr); 184 *local_addr = malloc (sizeof(**local_addr)); 185 if (*local_addr == NULL) 186 return ENOMEM; 187 krb5_copy_address(context, 188 auth_context->local_address, 189 *local_addr); 190 191 if(*remote_addr) 192 krb5_free_address (context, *remote_addr); 193 *remote_addr = malloc (sizeof(**remote_addr)); 194 if (*remote_addr == NULL) 195 return ENOMEM; 196 krb5_copy_address(context, 197 auth_context->remote_address, 198 *remote_addr); 199 return 0; 200 } 201 202 static krb5_error_code 203 copy_key(krb5_context context, 204 krb5_keyblock *in, 205 krb5_keyblock **out) 206 { 207 if(in) 208 return krb5_copy_keyblock(context, in, out); 209 *out = NULL; /* is this right? */ 210 return 0; 211 } 212 213 krb5_error_code 214 krb5_auth_con_getkey(krb5_context context, 215 krb5_auth_context auth_context, 216 krb5_keyblock **keyblock) 217 { 218 return copy_key(context, auth_context->keyblock, keyblock); 219 } 220 221 krb5_error_code 222 krb5_auth_con_getlocalsubkey(krb5_context context, 223 krb5_auth_context auth_context, 224 krb5_keyblock **keyblock) 225 { 226 return copy_key(context, auth_context->local_subkey, keyblock); 227 } 228 229 krb5_error_code 230 krb5_auth_con_getremotesubkey(krb5_context context, 231 krb5_auth_context auth_context, 232 krb5_keyblock **keyblock) 233 { 234 return copy_key(context, auth_context->remote_subkey, keyblock); 235 } 236 237 krb5_error_code 238 krb5_auth_con_setkey(krb5_context context, 239 krb5_auth_context auth_context, 240 krb5_keyblock *keyblock) 241 { 242 if(auth_context->keyblock) 243 krb5_free_keyblock(context, auth_context->keyblock); 244 return copy_key(context, keyblock, &auth_context->keyblock); 245 } 246 247 krb5_error_code 248 krb5_auth_con_setlocalsubkey(krb5_context context, 249 krb5_auth_context auth_context, 250 krb5_keyblock *keyblock) 251 { 252 if(auth_context->local_subkey) 253 krb5_free_keyblock(context, auth_context->local_subkey); 254 return copy_key(context, keyblock, &auth_context->local_subkey); 255 } 256 257 krb5_error_code 258 krb5_auth_con_setremotesubkey(krb5_context context, 259 krb5_auth_context auth_context, 260 krb5_keyblock *keyblock) 261 { 262 if(auth_context->remote_subkey) 263 krb5_free_keyblock(context, auth_context->remote_subkey); 264 return copy_key(context, keyblock, &auth_context->remote_subkey); 265 } 266 267 krb5_error_code 268 krb5_auth_setcksumtype(krb5_context context, 269 krb5_auth_context auth_context, 270 krb5_cksumtype cksumtype) 271 { 272 auth_context->cksumtype = cksumtype; 273 return 0; 274 } 275 276 krb5_error_code 277 krb5_auth_getcksumtype(krb5_context context, 278 krb5_auth_context auth_context, 279 krb5_cksumtype *cksumtype) 280 { 281 *cksumtype = auth_context->cksumtype; 282 return 0; 283 } 284 285 krb5_error_code 286 krb5_auth_setkeytype (krb5_context context, 287 krb5_auth_context auth_context, 288 krb5_keytype keytype) 289 { 290 auth_context->keytype = keytype; 291 return 0; 292 } 293 294 krb5_error_code 295 krb5_auth_getkeytype (krb5_context context, 296 krb5_auth_context auth_context, 297 krb5_keytype *keytype) 298 { 299 *keytype = auth_context->keytype; 300 return 0; 301 } 302 303 #if 0 304 krb5_error_code 305 krb5_auth_setenctype(krb5_context context, 306 krb5_auth_context auth_context, 307 krb5_enctype etype) 308 { 309 if(auth_context->keyblock) 310 krb5_free_keyblock(context, auth_context->keyblock); 311 ALLOC(auth_context->keyblock, 1); 312 if(auth_context->keyblock == NULL) 313 return ENOMEM; 314 auth_context->keyblock->keytype = etype; 315 return 0; 316 } 317 318 krb5_error_code 319 krb5_auth_getenctype(krb5_context context, 320 krb5_auth_context auth_context, 321 krb5_enctype *etype) 322 { 323 krb5_abortx(context, "unimplemented krb5_auth_getenctype called"); 324 } 325 #endif 326 327 krb5_error_code 328 krb5_auth_getlocalseqnumber(krb5_context context, 329 krb5_auth_context auth_context, 330 int32_t *seqnumber) 331 { 332 *seqnumber = auth_context->local_seqnumber; 333 return 0; 334 } 335 336 krb5_error_code 337 krb5_auth_setlocalseqnumber (krb5_context context, 338 krb5_auth_context auth_context, 339 int32_t seqnumber) 340 { 341 auth_context->local_seqnumber = seqnumber; 342 return 0; 343 } 344 345 krb5_error_code 346 krb5_auth_getremoteseqnumber(krb5_context context, 347 krb5_auth_context auth_context, 348 int32_t *seqnumber) 349 { 350 *seqnumber = auth_context->remote_seqnumber; 351 return 0; 352 } 353 354 krb5_error_code 355 krb5_auth_setremoteseqnumber (krb5_context context, 356 krb5_auth_context auth_context, 357 int32_t seqnumber) 358 { 359 auth_context->remote_seqnumber = seqnumber; 360 return 0; 361 } 362 363 364 krb5_error_code 365 krb5_auth_getauthenticator(krb5_context context, 366 krb5_auth_context auth_context, 367 krb5_authenticator *authenticator) 368 { 369 *authenticator = malloc(sizeof(**authenticator)); 370 if (*authenticator == NULL) 371 return ENOMEM; 372 373 copy_Authenticator(auth_context->authenticator, 374 *authenticator); 375 return 0; 376 } 377 378 379 void 380 krb5_free_authenticator(krb5_context context, 381 krb5_authenticator *authenticator) 382 { 383 free_Authenticator (*authenticator); 384 free (*authenticator); 385 *authenticator = NULL; 386 } 387 388 389 krb5_error_code 390 krb5_auth_con_setuserkey(krb5_context context, 391 krb5_auth_context auth_context, 392 krb5_keyblock *keyblock) 393 { 394 if(auth_context->keyblock) 395 krb5_free_keyblock(context, auth_context->keyblock); 396 return krb5_copy_keyblock(context, keyblock, &auth_context->keyblock); 397 } 398 399 #if 0 /* not implemented */ 400 401 krb5_error_code 402 krb5_auth_con_initivector(krb5_context context, 403 krb5_auth_context auth_context) 404 { 405 krb5_abortx(context, "unimplemented krb5_auth_con_initivector called"); 406 } 407 408 409 krb5_error_code 410 krb5_auth_con_setivector(krb5_context context, 411 krb5_auth_context auth_context, 412 krb5_pointer ivector) 413 { 414 krb5_abortx(context, "unimplemented krb5_auth_con_setivector called"); 415 } 416 417 418 krb5_error_code 419 krb5_auth_con_setrcache(krb5_context context, 420 krb5_auth_context auth_context, 421 krb5_rcache rcache) 422 { 423 krb5_abortx(context, "unimplemented krb5_auth_con_setrcache called"); 424 } 425 426 #endif /* not implemented */ 427