1 /* 2 * lib/krb5/krb/bld_princ.c 3 * 4 * Copyright 1991 by the Massachusetts Institute of Technology. 5 * All Rights Reserved. 6 * 7 * Export of this software from the United States of America may 8 * require a specific license from the United States Government. 9 * It is the responsibility of any person or organization contemplating 10 * export to obtain such a license before exporting. 11 * 12 * WITHIN THAT CONSTRAINT, permission to use, copy, modify, and 13 * distribute this software and its documentation for any purpose and 14 * without fee is hereby granted, provided that the above copyright 15 * notice appear in all copies and that both that copyright notice and 16 * this permission notice appear in supporting documentation, and that 17 * the name of M.I.T. not be used in advertising or publicity pertaining 18 * to distribution of the software without specific, written prior 19 * permission. Furthermore if you modify this software you must label 20 * your software as modified software and not distribute it in such a 21 * fashion that it might be confused with the original M.I.T. software. 22 * M.I.T. makes no representations about the suitability of 23 * this software for any purpose. It is provided "as is" without express 24 * or implied warranty. 25 * 26 * 27 * Build a principal from a list of strings 28 */ 29 30 #include <stdarg.h> 31 #include "k5-int.h" 32 33 /*ARGSUSED*/ 34 krb5_error_code 35 KRB5_CALLCONV 36 krb5_build_principal_va(krb5_context context, krb5_principal princ, unsigned int rlen, const char *realm, va_list ap) 37 { 38 register int i, count = 0; 39 register char *next; 40 char *tmpdata; 41 krb5_data *data; 42 43 /* guess at an initial sufficent count of 2 pieces */ 44 count = 2; 45 46 /* get space for array and realm, and insert realm */ 47 data = (krb5_data *) malloc(sizeof(krb5_data) * count); 48 if (data == 0) 49 return ENOMEM; 50 krb5_princ_set_realm_length(context, princ, rlen); 51 tmpdata = malloc(rlen); 52 if (!tmpdata) { 53 free (data); 54 return ENOMEM; 55 } 56 krb5_princ_set_realm_data(context, princ, tmpdata); 57 memcpy(tmpdata, realm, rlen); 58 59 /* process rest of components */ 60 61 for (i = 0, next = va_arg(ap, char *); 62 next; 63 next = va_arg(ap, char *), i++) { 64 if (i == count) { 65 /* not big enough. realloc the array */ 66 krb5_data *p_tmp; 67 p_tmp = (krb5_data *) realloc((char *)data, 68 sizeof(krb5_data)*(count*2)); 69 if (!p_tmp) { 70 free_out: 71 while (--i >= 0) 72 krb5_xfree(data[i].data); 73 krb5_xfree(data); 74 krb5_xfree(tmpdata); 75 return (ENOMEM); 76 } 77 count *= 2; 78 data = p_tmp; 79 } 80 81 data[i].length = strlen(next); 82 data[i].data = strdup(next); 83 if (!data[i].data) 84 goto free_out; 85 } 86 princ->data = data; 87 princ->length = i; 88 princ->type = KRB5_NT_UNKNOWN; 89 princ->magic = KV5M_PRINCIPAL; 90 return 0; 91 } 92 93 krb5_error_code KRB5_CALLCONV_C 94 krb5_build_principal(krb5_context context, krb5_principal * princ, 95 unsigned int rlen, 96 const char * realm, ...) 97 { 98 va_list ap; 99 krb5_error_code retval; 100 krb5_principal pr_ret = (krb5_principal)malloc(sizeof(krb5_principal_data)); 101 102 if (!pr_ret) 103 return ENOMEM; 104 105 va_start(ap, realm); 106 retval = krb5_build_principal_va(context, pr_ret, rlen, realm, ap); 107 va_end(ap); 108 if (retval == 0) 109 *princ = pr_ret; 110 return retval; 111 } 112