static krb5_error_code krb5_store_xdr_data(krb5_storage *sp, krb5_data data) { u_char zero[4] = {0, 0, 0, 0}; int ret; size_t pad; ret = krb5_store_int32(sp, data.length); if(ret < 0) return ret; ret = krb5_storage_write(sp, data.data, data.length); if(ret != data.length){ if(ret < 0) return errno; return KRB5_CC_END; } pad = (4 - data.length % 4) % 4; if (pad) { ret = krb5_storage_write(sp, zero, pad); if (ret != pad) { if (ret < 0) return errno; return KRB5_CC_END; } } return 0; }
krb5_error_code KRB5_LIB_FUNCTION _krb5_krb_create_ciph(krb5_context context, const krb5_keyblock *session, const char *service, const char *instance, const char *realm, uint32_t life, unsigned char kvno, const krb5_data *ticket, uint32_t kdc_time, const krb5_keyblock *key, krb5_data *enc_data) { krb5_error_code ret; krb5_storage *sp; krb5_data_zero(enc_data); sp = krb5_storage_emem(); if (sp == NULL) { krb5_set_error_string(context, "malloc: out of memory"); return ENOMEM; } krb5_storage_set_byteorder(sp, KRB5_STORAGE_BYTEORDER_BE); /* session key */ ret = krb5_storage_write(sp, session->keyvalue.data, session->keyvalue.length); if (ret != session->keyvalue.length) { ret = EINVAL; goto error; } RCHECK(ret, put_nir(sp, service, instance, realm), error); RCHECK(ret, krb5_store_int8(sp, life), error); RCHECK(ret, krb5_store_int8(sp, kvno), error); RCHECK(ret, krb5_store_int8(sp, ticket->length), error); ret = krb5_storage_write(sp, ticket->data, ticket->length); if (ret != ticket->length) { ret = EINVAL; goto error; } RCHECK(ret, krb5_store_int32(sp, kdc_time), error); ret = storage_to_etext(context, sp, key, enc_data); error: krb5_storage_free(sp); if (ret) krb5_set_error_string(context, "Failed to encode kerberos 4 ticket"); return ret; }
int krb_mk_req(KTEXT authent, char *service, char *instance, char *realm, int32_t checksum) #endif { CREDENTIALS cr; KTEXT_ST req; krb5_storage *sp; int code; /* XXX get user realm */ const char *myrealm = realm; krb5_data a; code = krb_get_cred(service, instance, realm, &cr); if(code || time(NULL) > krb_life_to_time(cr.issue_date, cr.lifetime)){ code = get_ad_tkt((char *)service, (char *)instance, (char *)realm, lifetime); if(code == KSUCCESS) code = krb_get_cred(service, instance, realm, &cr); } if(code) return code; sp = krb5_storage_emem(); krb5_store_int8(sp, KRB_PROT_VERSION); krb5_store_int8(sp, AUTH_MSG_APPL_REQUEST); krb5_store_int8(sp, cr.kvno); krb5_store_stringz(sp, realm); krb5_store_int8(sp, cr.ticket_st.length); build_request(&req, cr.pname, cr.pinst, myrealm, checksum); encrypt_ktext(&req, &cr.session, DES_ENCRYPT); krb5_store_int8(sp, req.length); krb5_storage_write(sp, cr.ticket_st.dat, cr.ticket_st.length); krb5_storage_write(sp, req.dat, req.length); krb5_storage_to_data(sp, &a); krb5_storage_free(sp); memcpy(authent->dat, a.data, a.length); authent->length = a.length; krb5_data_free(&a); memset(&cr, 0, sizeof(cr)); memset(&req, 0, sizeof(req)); return KSUCCESS; }
krb5_error_code KRB5_LIB_FUNCTION _krb5_krb_tf_setup(krb5_context context, struct credentials *v4creds, const char *tkfile, int append) { krb5_error_code ret; krb5_storage *sp; sp = krb5_storage_emem(); if (sp == NULL) return ENOMEM; krb5_storage_set_byteorder(sp, KRB5_STORAGE_BYTEORDER_HOST); krb5_storage_set_eof_code(sp, KRB5_CC_IO); krb5_clear_error_string(context); if (!append) { RCHECK(ret, krb5_store_stringz(sp, v4creds->pname), error); RCHECK(ret, krb5_store_stringz(sp, v4creds->pinst), error); } /* cred */ RCHECK(ret, krb5_store_stringz(sp, v4creds->service), error); RCHECK(ret, krb5_store_stringz(sp, v4creds->instance), error); RCHECK(ret, krb5_store_stringz(sp, v4creds->realm), error); ret = krb5_storage_write(sp, v4creds->session, 8); if (ret != 8) { ret = KRB5_CC_IO; goto error; } RCHECK(ret, krb5_store_int32(sp, v4creds->lifetime), error); RCHECK(ret, krb5_store_int32(sp, v4creds->kvno), error); RCHECK(ret, krb5_store_int32(sp, v4creds->ticket_st.length), error); ret = krb5_storage_write(sp, v4creds->ticket_st.dat, v4creds->ticket_st.length); if (ret != v4creds->ticket_st.length) { ret = KRB5_CC_IO; goto error; } RCHECK(ret, krb5_store_int32(sp, v4creds->issue_date), error); ret = write_v4_cc(context, tkfile, sp, append); error: krb5_storage_free(sp); return ret; }
KRB5_LIB_FUNCTION krb5_error_code KRB5_LIB_CALL _krb5_s4u2self_to_checksumdata(krb5_context context, const PA_S4U2Self *self, krb5_data *data) { krb5_error_code ret; krb5_ssize_t ssize; krb5_storage *sp; size_t size; size_t i; sp = krb5_storage_emem(); if (sp == NULL) { krb5_clear_error_message(context); return ENOMEM; } krb5_storage_set_flags(sp, KRB5_STORAGE_BYTEORDER_LE); ret = krb5_store_int32(sp, self->name.name_type); if (ret) goto out; for (i = 0; i < self->name.name_string.len; i++) { size = strlen(self->name.name_string.val[i]); ssize = krb5_storage_write(sp, self->name.name_string.val[i], size); if (ssize != (krb5_ssize_t)size) { ret = ENOMEM; goto out; } } size = strlen(self->realm); ssize = krb5_storage_write(sp, self->realm, size); if (ssize != (krb5_ssize_t)size) { ret = ENOMEM; goto out; } size = strlen(self->auth); ssize = krb5_storage_write(sp, self->auth, size); if (ssize != (krb5_ssize_t)size) { ret = ENOMEM; goto out; } ret = krb5_storage_to_data(sp, data); krb5_storage_free(sp); return ret; out: krb5_clear_error_message(context); return ret; }
krb5_error_code kcm_ccache_get_uuids(krb5_context context, kcm_client *client, kcm_operation opcode, krb5_storage *sp) { krb5_error_code ret; kcm_ccache p; ret = KRB5_FCC_NOFILE; HEIMDAL_MUTEX_lock(&ccache_mutex); for (p = ccache_head; p != NULL; p = p->next) { if ((p->flags & KCM_FLAGS_VALID) == 0) continue; ret = kcm_access(context, client, opcode, p); if (ret) { ret = 0; continue; } krb5_storage_write(sp, p->uuid, sizeof(p->uuid)); } HEIMDAL_MUTEX_unlock(&ccache_mutex); return ret; }
krb5_error_code hdb_print_entry(krb5_context context, HDB *db, hdb_entry_ex *entry, void *data) { struct hdb_print_entry_arg *parg = data; krb5_error_code ret; krb5_storage *sp; fflush(parg->out); sp = krb5_storage_from_fd(fileno(parg->out)); if (sp == NULL) { krb5_set_error_message(context, ENOMEM, "malloc: out of memory"); return ENOMEM; } switch (parg->fmt) { case HDB_DUMP_HEIMDAL: ret = entry2string_int(context, sp, &entry->entry); break; case HDB_DUMP_MIT: ret = entry2mit_string_int(context, sp, &entry->entry); break; default: heim_abort("Only two dump formats supported: Heimdal and MIT"); } if (ret) { krb5_storage_free(sp); return ret; } krb5_storage_write(sp, "\n", 1); krb5_storage_free(sp); return 0; }
krb5_error_code hdb_print_entry(krb5_context context, HDB *db, hdb_entry_ex *entry, void *data) { krb5_error_code ret; krb5_storage *sp; FILE *f = data; fflush(f); sp = krb5_storage_from_fd(fileno(f)); if(sp == NULL) { krb5_set_error_message(context, ENOMEM, "malloc: out of memory"); return ENOMEM; } ret = entry2string_int(context, sp, &entry->entry); if(ret) { krb5_storage_free(sp); return ret; } krb5_storage_write(sp, "\n", 1); krb5_storage_free(sp); return 0; }
krb5_error_code hdb_entry2string (krb5_context context, hdb_entry *ent, char **str) { krb5_error_code ret; krb5_data data; krb5_storage *sp; sp = krb5_storage_emem(); if(sp == NULL) { krb5_set_error_message(context, ENOMEM, "malloc: out of memory"); return ENOMEM; } ret = entry2string_int(context, sp, ent); if(ret) { krb5_storage_free(sp); return ret; } krb5_storage_write(sp, "\0", 1); krb5_storage_to_data(sp, &data); krb5_storage_free(sp); *str = data.data; return 0; }
krb5_error_code krb5_store_uuid(krb5_storage *sp, krb5_uuid uuid) { ssize_t sret; sret = krb5_storage_write(sp, uuid, sizeof(krb5_uuid)); if (sret != sizeof(krb5_uuid)) return HEIM_ERR_STORAGE_UUID; return 0; }
/* * Request: * NameZ * Cursor * * Response: * Creds */ static krb5_error_code kcm_get_next (krb5_context context, krb5_ccache id, krb5_cc_cursor *cursor, krb5_creds *creds) { krb5_error_code ret; krb5_kcmcache *k = KCMCACHE(id); krb5_kcm_cursor c = KCMCURSOR(*cursor); krb5_storage *request, *response; krb5_data response_data; ssize_t sret; again: if (c->offset >= c->length) return KRB5_CC_END; ret = krb5_kcm_storage_request(context, KCM_OP_GET_CRED_BY_UUID, &request); if (ret) return ret; ret = krb5_store_stringz(request, k->name); if (ret) { krb5_storage_free(request); return ret; } sret = krb5_storage_write(request, &c->uuids[c->offset], sizeof(c->uuids[c->offset])); c->offset++; if (sret != sizeof(c->uuids[c->offset])) { krb5_storage_free(request); krb5_clear_error_message(context); return ENOMEM; } ret = krb5_kcm_call(context, request, &response, &response_data); krb5_storage_free(request); if (ret == KRB5_CC_END) { goto again; } else if (ret) return ret; ret = krb5_ret_creds(response, creds); if (ret) ret = KRB5_CC_IO; krb5_storage_free(response); krb5_data_free(&response_data); return ret; }
static krb5_error_code kcm_op_add_ntlm_cred(krb5_context context, kcm_client *client, kcm_operation opcode, krb5_storage *request, krb5_storage *response) { struct kcm_ntlm_cred *cred, *c; krb5_error_code ret; cred = calloc(1, sizeof(*cred)); if (cred == NULL) return ENOMEM; RAND_bytes(cred->uuid, sizeof(cred->uuid)); ret = krb5_ret_stringz(request, &cred->user); if (ret) goto error; ret = krb5_ret_stringz(request, &cred->domain); if (ret) goto error; ret = krb5_ret_data(request, &cred->nthash); if (ret) goto error; /* search for dups */ c = find_ntlm_cred(cred->user, cred->domain, client); if (c) { krb5_data hash = c->nthash; c->nthash = cred->nthash; cred->nthash = hash; free_cred(cred); cred = c; } else { cred->next = ntlm_head; ntlm_head = cred; } cred->uid = client->uid; cred->session = client->session; /* write response */ (void)krb5_storage_write(response, &cred->uuid, sizeof(cred->uuid)); return 0; error: free_cred(cred); return ret; }
krb5_error_code KRB5_LIB_FUNCTION _krb5_krb_create_ticket(krb5_context context, unsigned char flags, const char *pname, const char *pinstance, const char *prealm, int32_t paddress, const krb5_keyblock *session, int16_t life, int32_t life_sec, const char *sname, const char *sinstance, const krb5_keyblock *key, krb5_data *enc_data) { krb5_error_code ret; krb5_storage *sp; krb5_data_zero(enc_data); sp = krb5_storage_emem(); if (sp == NULL) { krb5_set_error_string(context, "malloc: out of memory"); return ENOMEM; } krb5_storage_set_byteorder(sp, KRB5_STORAGE_BYTEORDER_BE); RCHECK(ret, krb5_store_int8(sp, flags), error); RCHECK(ret, put_nir(sp, pname, pinstance, prealm), error); RCHECK(ret, krb5_store_int32(sp, ntohl(paddress)), error); /* session key */ ret = krb5_storage_write(sp, session->keyvalue.data, session->keyvalue.length); if (ret != session->keyvalue.length) { ret = EINVAL; goto error; } RCHECK(ret, krb5_store_int8(sp, life), error); RCHECK(ret, krb5_store_int32(sp, life_sec), error); RCHECK(ret, put_nir(sp, sname, sinstance, NULL), error); ret = storage_to_etext(context, sp, key, enc_data); error: krb5_storage_free(sp); if (ret) krb5_set_error_string(context, "Failed to encode kerberos 4 ticket"); return ret; }
static krb5_error_code kcm_get_cache_next(krb5_context context, krb5_cc_cursor cursor, const krb5_cc_ops *ops, krb5_ccache *id) { krb5_error_code ret; krb5_kcm_cursor c = KCMCURSOR(cursor); krb5_storage *request, *response; krb5_data response_data; ssize_t sret; char *name; *id = NULL; again: if (c->offset >= c->length) return KRB5_CC_END; ret = krb5_kcm_storage_request(context, KCM_OP_GET_CACHE_BY_UUID, &request); if (ret) return ret; sret = krb5_storage_write(request, &c->uuids[c->offset], sizeof(c->uuids[c->offset])); c->offset++; if (sret != sizeof(c->uuids[c->offset])) { krb5_storage_free(request); krb5_clear_error_message(context); return ENOMEM; } ret = krb5_kcm_call(context, request, &response, &response_data); krb5_storage_free(request); if (ret == KRB5_FCC_NOFILE) { /* cache no longer exists, try next */ goto again; } else if (ret) return ret; ret = krb5_ret_stringz(response, &name); krb5_storage_free(response); krb5_data_free(&response_data); if (ret) return ret; ret = _krb5_cc_allocate(context, ops, id); if (ret == 0) ret = kcm_alloc(context, name, id); krb5_xfree(name); return ret; }
krb5_error_code store_string(krb5_storage *sp, const char *str) { size_t len = strlen(str) + 1; krb5_error_code ret; ret = krb5_store_int32(sp, len); if (ret) return ret; ret = krb5_storage_write(sp, str, len); if (ret != len) return EINVAL; return 0; }
kadm5_ret_t kadm5_log_modify (kadm5_server_context *context, hdb_entry *ent, u_int32_t mask) { krb5_storage *sp; kadm5_ret_t ret; krb5_data value; u_int32_t len; kadm5_log_context *log_context = &context->log_context; krb5_data_zero(&value); sp = krb5_storage_emem(); ret = hdb_entry2value (context->context, ent, &value); if (ret) goto failed; ret = kadm5_log_preamble (context, sp, kadm_modify); if (ret) goto failed; len = value.length + 4; ret = krb5_store_int32 (sp, len); if (ret) goto failed; ret = krb5_store_int32 (sp, mask); if (ret) goto failed; krb5_storage_write (sp, value.data, value.length); ret = krb5_store_int32 (sp, len); if (ret) goto failed; ret = kadm5_log_postamble (log_context, sp); if (ret) goto failed; ret = kadm5_log_flush (log_context, sp); if (ret) goto failed; krb5_data_free(&value); krb5_storage_free (sp); return kadm5_log_end (context); failed: krb5_data_free(&value); krb5_storage_free(sp); return ret; }
krb5_error_code KRB5_LIB_FUNCTION _krb5_krb_create_auth_reply(krb5_context context, const char *pname, const char *pinst, const char *prealm, int32_t time_ws, int n, uint32_t x_date, unsigned char kvno, const krb5_data *cipher, krb5_data *data) { krb5_error_code ret; krb5_storage *sp; krb5_data_zero(data); sp = krb5_storage_emem(); if (sp == NULL) { krb5_set_error_string(context, "malloc: out of memory"); return ENOMEM; } krb5_storage_set_byteorder(sp, KRB5_STORAGE_BYTEORDER_BE); RCHECK(ret, krb5_store_int8(sp, KRB_PROT_VERSION), error); RCHECK(ret, krb5_store_int8(sp, AUTH_MSG_KDC_REPLY), error); RCHECK(ret, put_nir(sp, pname, pinst, prealm), error); RCHECK(ret, krb5_store_int32(sp, time_ws), error); RCHECK(ret, krb5_store_int8(sp, n), error); RCHECK(ret, krb5_store_int32(sp, x_date), error); RCHECK(ret, krb5_store_int8(sp, kvno), error); RCHECK(ret, krb5_store_int16(sp, cipher->length), error); ret = krb5_storage_write(sp, cipher->data, cipher->length); if (ret != cipher->length) { ret = EINVAL; goto error; } ret = krb5_storage_to_data(sp, data); error: krb5_storage_free(sp); if (ret) krb5_set_error_string(context, "Failed to encode kerberos 4 ticket"); return ret; }
static krb5_error_code krb5_kt_store_string(krb5_storage *sp, heim_general_string data) { int ret; size_t len = strlen(data); ret = krb5_store_int16(sp, len); if(ret < 0) return ret; ret = krb5_storage_write(sp, data, len); if(ret != (int)len){ if(ret < 0) return errno; return KRB5_KT_END; } return 0; }
static krb5_error_code krb5_kt_store_data(krb5_context context, krb5_storage *sp, krb5_data data) { int ret; ret = krb5_store_int16(sp, data.length); if(ret < 0) return ret; ret = krb5_storage_write(sp, data.data, data.length); if(ret != (int)data.length){ if(ret < 0) return errno; return KRB5_KT_END; } return 0; }
static krb5_error_code append_string(krb5_context context, krb5_storage *sp, const char *fmt, ...) { krb5_error_code ret; char *s; va_list ap; va_start(ap, fmt); vasprintf(&s, fmt, ap); va_end(ap); if(s == NULL) { krb5_set_error_message(context, ENOMEM, "malloc: out of memory"); return ENOMEM; } ret = krb5_storage_write(sp, s, strlen(s)); free(s); return ret; }
/* * These utility functions return the number of bytes written or -1, and * they set an error in the context. */ static ssize_t append_string(krb5_context context, krb5_storage *sp, const char *fmt, ...) { ssize_t sz; char *s; int rc; va_list ap; va_start(ap, fmt); rc = vasprintf(&s, fmt, ap); va_end(ap); if(rc < 0) { krb5_set_error_message(context, ENOMEM, "malloc: out of memory"); return -1; } sz = krb5_storage_write(sp, s, strlen(s)); free(s); return sz; }
static krb5_error_code fill_zeros(krb5_context context, krb5_storage *sp, size_t len) { ssize_t sret; size_t l; while (len) { l = len; if (l > sizeof(zeros)) l = sizeof(zeros); sret = krb5_storage_write(sp, zeros, l); if (sret <= 0) return krb5_enomem(context); len -= sret; } return 0; }
krb5_error_code _kadm5_xdr_store_data_xdr(krb5_storage *sp, krb5_data data) { krb5_error_code ret; ssize_t sret; size_t res; ret = krb5_store_data(sp, data); if (ret) return ret; res = 4 - (data.length % 4); if (res != 4) { static const char zero[4] = { 0, 0, 0, 0 }; sret = krb5_storage_write(sp, zero, res); if(sret < 0 || (size_t)sret != res) return (sret < 0)? errno : krb5_storage_get_eof_code(sp); } return 0; }
static krb5_error_code KRB5_CALLCONV fkt_remove_entry(krb5_context context, krb5_keytab id, krb5_keytab_entry *entry) { krb5_keytab_entry e; krb5_kt_cursor cursor; off_t pos_start, pos_end; int found = 0; krb5_error_code ret; ret = fkt_start_seq_get_int(context, id, O_RDWR | O_BINARY | O_CLOEXEC, 1, &cursor); if(ret != 0) goto out; /* return other error here? */ while(fkt_next_entry_int(context, id, &e, &cursor, &pos_start, &pos_end) == 0) { if(krb5_kt_compare(context, &e, entry->principal, entry->vno, entry->keyblock.keytype)) { int32_t len; unsigned char buf[128]; found = 1; krb5_storage_seek(cursor.sp, pos_start, SEEK_SET); len = pos_end - pos_start - 4; krb5_store_int32(cursor.sp, -len); memset(buf, 0, sizeof(buf)); while(len > 0) { krb5_storage_write(cursor.sp, buf, min((size_t)len, sizeof(buf))); len -= min((size_t)len, sizeof(buf)); } } krb5_kt_free_entry(context, &e); } krb5_kt_end_seq_get(context, id, &cursor); out: if (!found) { krb5_clear_error_message (context); return KRB5_KT_NOTFOUND; } return 0; }
static krb5_error_code storage_to_etext(krb5_context context, krb5_storage *sp, const krb5_keyblock *key, krb5_data *enc_data) { krb5_error_code ret; krb5_crypto crypto; krb5_ssize_t size; krb5_data data; /* multiple of eight bytes */ size = krb5_storage_seek(sp, 0, SEEK_END); if (size < 0) return EINVAL; size = 8 - (size & 7); ret = krb5_storage_write(sp, eightzeros, size); if (ret != size) return EINVAL; ret = krb5_storage_to_data(sp, &data); if (ret) return ret; ret = krb5_crypto_init(context, key, ETYPE_DES_PCBC_NONE, &crypto); if (ret) { krb5_data_free(&data); return ret; } ret = krb5_encrypt(context, crypto, 0, data.data, data.length, enc_data); krb5_data_free(&data); krb5_crypto_destroy(context, crypto); return ret; }
static void storage_printf(krb5_storage *sp, const char *fmt, ...) { size_t len; ssize_t ret; va_list ap; char *str; va_start(ap, fmt); vasprintf(&str, fmt, ap); va_end(ap); if (str == NULL) errx(1, "vasprintf"); len = strlen(str); ret = krb5_storage_write(sp, str, len); if (ret < 0 || (size_t)ret != len) errx(1, "failed to write to server"); free(str); }
kadm5_ret_t kadm5_log_create (kadm5_server_context *context, hdb_entry *ent) { krb5_storage *sp; kadm5_ret_t ret; krb5_data value; kadm5_log_context *log_context = &context->log_context; sp = krb5_storage_emem(); ret = hdb_entry2value (context->context, ent, &value); if (ret) { krb5_storage_free(sp); return ret; } ret = kadm5_log_preamble (context, sp, kadm_create); if (ret) { krb5_data_free (&value); krb5_storage_free(sp); return ret; } krb5_store_int32 (sp, value.length); krb5_storage_write(sp, value.data, value.length); krb5_store_int32 (sp, value.length); krb5_data_free (&value); ret = kadm5_log_postamble (log_context, sp); if (ret) { krb5_storage_free (sp); return ret; } ret = kadm5_log_flush (log_context, sp); krb5_storage_free (sp); if (ret) return ret; ret = kadm5_log_end (context); return ret; }
/* * Request: * NameZ * * Response: * UUIDs * */ static krb5_error_code kcm_op_get_cred_uuid_list(krb5_context context, kcm_client *client, kcm_operation opcode, krb5_storage *request, krb5_storage *response) { struct kcm_creds *creds; krb5_error_code ret; kcm_ccache ccache; char *name; ret = krb5_ret_stringz(request, &name); if (ret) return ret; KCM_LOG_REQUEST_NAME(context, client, opcode, name); ret = kcm_ccache_resolve_client(context, client, opcode, name, &ccache); free(name); if (ret) return ret; for (creds = ccache->creds ; creds ; creds = creds->next) { ssize_t sret; sret = krb5_storage_write(response, &creds->uuid, sizeof(creds->uuid)); if (sret != sizeof(creds->uuid)) { ret = ENOMEM; break; } } kcm_release_ccache(context, ccache); return ret; }
static krb5_error_code resolve_by_uuid_oid(krb5_context context, const krb5_cc_ops *ops, krb5_ccache id, krb5_uuid uuid) { krb5_storage *request, *response; krb5_data response_data; krb5_error_code ret; char *name; ssize_t sret; ret = krb5_kcm_storage_request(context, KCM_OP_GET_CACHE_BY_UUID, &request); if (ret) return ret; sret = krb5_storage_write(request, uuid, sizeof(krb5_uuid)); if (sret != sizeof(krb5_uuid)) { krb5_storage_free(request); krb5_clear_error_message(context); return ENOMEM; } ret = krb5_kcm_call(context, request, &response, &response_data); krb5_storage_free(request); if (ret) return ret; ret = krb5_ret_stringz(response, &name); krb5_storage_free(response); krb5_data_free(&response_data); if (ret) return ret; ret = kcm_alloc(context, name, &id); krb5_xfree(name); return ret; }
/* * Request: * * Response: * */ krb5_error_code _krb5_kcm_ntlm_challenge(krb5_context context, int op __attribute((__unused__)), uint8_t chal[8]) { krb5_error_code ret; krb5_ssize_t sret; krb5_storage *request; ret = krb5_kcm_storage_request(context, KCM_OP_ADD_NTLM_CHALLENGE, &request); if (ret) return ret; sret = krb5_storage_write(request, chal, 8); if (sret != 8) { ret = EINVAL; goto out; } ret = krb5_kcm_call(context, request, NULL, NULL); out: krb5_storage_free(request); return ret; }