summaryrefslogtreecommitdiffstats
path: root/src/kdc/do_as_req.c
diff options
context:
space:
mode:
authorSam Hartman <hartmans@mit.edu>2009-03-31 17:00:41 +0000
committerSam Hartman <hartmans@mit.edu>2009-03-31 17:00:41 +0000
commitd1384be39be11423bd05b88ec444733361fc1467 (patch)
treef577c2d27f9f96c1c3633c740bbf02b606534650 /src/kdc/do_as_req.c
parent22810910e3c834ee0bc66d0c96369c43e780a2bb (diff)
downloadkrb5-d1384be39be11423bd05b88ec444733361fc1467.tar.gz
krb5-d1384be39be11423bd05b88ec444733361fc1467.tar.xz
krb5-d1384be39be11423bd05b88ec444733361fc1467.zip
Implement FAST from draft-ietf-krb-wg-preauth-framework
Merge fast branch at 22146 onto trunk Implement the kerberos pre-authentication framework FAST feature per Projects/FAST on the wiki. ticket: 6436 Target_Version: 1.7 git-svn-id: svn://anonsvn.mit.edu/krb5/trunk@22149 dc483132-0cff-0310-8789-dd5450dbe970
Diffstat (limited to 'src/kdc/do_as_req.c')
-rw-r--r--src/kdc/do_as_req.c66
1 files changed, 61 insertions, 5 deletions
diff --git a/src/kdc/do_as_req.c b/src/kdc/do_as_req.c
index 8db39ac4f2..7b590f4e01 100644
--- a/src/kdc/do_as_req.c
+++ b/src/kdc/do_as_req.c
@@ -82,7 +82,7 @@
#endif
#endif /* APPLE_PKINIT */
-static krb5_error_code prepare_error_as (krb5_kdc_req *, int, krb5_data *,
+static krb5_error_code prepare_error_as (struct kdc_request_state *, krb5_kdc_req *, int, krb5_data *,
krb5_principal, krb5_data **,
const char *);
@@ -117,6 +117,9 @@ process_as_req(krb5_kdc_req *request, krb5_data *req_pkt,
int did_log = 0;
const char *emsg = 0;
krb5_keylist_node *tmp_mkey_list;
+ struct kdc_request_state *state = NULL;
+ krb5_data encoded_req_body;
+
#if APPLE_PKINIT
asReqDebug("process_as_req top realm %s name %s\n",
@@ -133,6 +136,22 @@ process_as_req(krb5_kdc_req *request, krb5_data *req_pkt,
session_key.contents = 0;
enc_tkt_reply.authorization_data = NULL;
+ errcode = kdc_make_rstate(&state);
+ if (errcode != 0) {
+ status = "constructing state";
+ goto errout;
+ }
+ if (fetch_asn1_field((unsigned char *) req_pkt->data,
+ 1, 4, &encoded_req_body) != 0) {
+ errcode = ASN1_BAD_ID;
+ status = "Finding req_body";
+}
+ errcode = kdc_find_fast(&request, &encoded_req_body, NULL /*TGS key*/, NULL, state);
+ if (errcode) {
+ status = "error decoding FAST";
+ goto errout;
+ }
+ request->kdc_state = state;
if (!request->client) {
status = "NULL_CLIENT";
errcode = KRB5KDC_ERR_C_PRINCIPAL_UNKNOWN;
@@ -548,6 +567,7 @@ process_as_req(krb5_kdc_req *request, krb5_data *req_pkt,
goto errout;
}
+
errcode = handle_authdata(kdc_context,
c_flags,
&client,
@@ -572,6 +592,11 @@ process_as_req(krb5_kdc_req *request, krb5_data *req_pkt,
goto errout;
}
ticket_reply.enc_part.kvno = server_key->key_data_kvno;
+ errcode = kdc_fast_response_handle_padata(state, request, &reply);
+ if (errcode) {
+ status = "fast response handling";
+ goto errout;
+ }
/* now encode/encrypt the response */
@@ -629,7 +654,7 @@ egress:
if (errcode < 0 || errcode > 128)
errcode = KRB_ERR_GENERIC;
- errcode = prepare_error_as(request, errcode, &e_data,
+ errcode = prepare_error_as(state, request, errcode, &e_data,
c_nprincs ? client.princ : NULL,
response, status);
status = 0;
@@ -679,18 +704,24 @@ egress:
}
krb5_free_data_contents(kdc_context, &e_data);
+ kdc_free_rstate(state);
+ request->kdc_state = NULL;
+ krb5_free_kdc_req(kdc_context, request);
assert(did_log != 0);
return errcode;
}
static krb5_error_code
-prepare_error_as (krb5_kdc_req *request, int error, krb5_data *e_data,
+prepare_error_as (struct kdc_request_state *rstate, krb5_kdc_req *request, int error, krb5_data *e_data,
krb5_principal canon_client, krb5_data **response,
const char *status)
{
krb5_error errpkt;
krb5_error_code retval;
krb5_data *scratch;
+ krb5_pa_data **pa = NULL;
+ krb5_typed_data **td = NULL;
+ size_t size;
errpkt.ctime = request->nonce;
errpkt.cusec = 0;
@@ -719,13 +750,38 @@ prepare_error_as (krb5_kdc_req *request, int error, krb5_data *e_data,
errpkt.e_data.length = 0;
errpkt.e_data.data = NULL;
}
-
+ /*We need to try and produce a padata sequence for FAST*/
+ retval = decode_krb5_padata_sequence(e_data, &pa);
+ if (retval != 0) {
+ retval = decode_krb5_typed_data(e_data, &td);
+ if (retval == 0) {
+ for (size =0; td[size]; size++);
+ pa = calloc(size+1, sizeof(*pa));
+ if (pa == NULL)
+ retval = ENOMEM;
+ else for (size = 0; td[size]; size++) {
+ krb5_pa_data *pad = malloc(sizeof(krb5_pa_data *));
+ if (pad == NULL) {
+ retval = ENOMEM;
+ break;
+ }
+ pad->pa_type = td[size]->type;
+ pad->contents = td[size]->data;
+ pad->length = td[size]->length;
+ pa[size] = pad;
+ }
+ krb5_free_typed_data(kdc_context, td);
+ }
+ }
+ retval = kdc_fast_handle_error(kdc_context, rstate,
+ request, pa, &errpkt);
+ if (retval == 0)
retval = krb5_mk_error(kdc_context, &errpkt, scratch);
free(errpkt.text.data);
if (retval)
free(scratch);
else
*response = scratch;
-
+ krb5_free_pa_data(kdc_context, pa);
return retval;
}