From ec440d343bcb8bd422fd468cab954991e08e03d4 Mon Sep 17 00:00:00 2001 From: Tom Yu Date: Tue, 4 Sep 2007 18:54:21 +0000 Subject: revert accidental commit of gc_frm_kdc.c ticket: 5707 git-svn-id: svn://anonsvn.mit.edu/krb5/trunk@19915 dc483132-0cff-0310-8789-dd5450dbe970 --- src/lib/krb5/krb/gc_frm_kdc.c | 201 +++++------------------------------------- 1 file changed, 20 insertions(+), 181 deletions(-) (limited to 'src') diff --git a/src/lib/krb5/krb/gc_frm_kdc.c b/src/lib/krb5/krb/gc_frm_kdc.c index e8fd072078..506538ca45 100644 --- a/src/lib/krb5/krb/gc_frm_kdc.c +++ b/src/lib/krb5/krb/gc_frm_kdc.c @@ -92,7 +92,6 @@ struct tr_state { krb5_creds *cur_cc_tgt; krb5_creds *nxt_cc_tgt; unsigned int ntgts; - krb5_creds *offpath_tgt; }; /* @@ -169,11 +168,7 @@ static krb5_error_code init_rtree(struct tr_state *, static krb5_error_code do_traversal(krb5_context ctx, krb5_ccache, krb5_principal client, krb5_principal server, krb5_creds *out_cc_tgt, krb5_creds **out_tgt, - krb5_creds ***out_kdc_tgts, int *tgtptr_isoffpath); -static krb5_error_code chase_offpath(struct tr_state *, krb5_principal, - krb5_principal); -static krb5_error_code offpath_loopchk(struct tr_state *ts, - krb5_creds *tgt, krb5_creds *reftgts[], int rcount); + krb5_creds ***out_kdc_tgts); static krb5_error_code krb5_get_cred_from_kdc_opt(krb5_context, krb5_ccache, krb5_creds *, krb5_creds **, krb5_creds ***, int); @@ -439,7 +434,6 @@ find_nxt_kdc(struct tr_state *ts) krb5_principal *kdcptr; TR_DBG(ts, "find_nxt_kdc"); - assert(ts->ntgts > 0); assert(ts->nxt_tgt == ts->kdc_tgts[ts->ntgts-1]); if (krb5_princ_size(ts->ctx, ts->nxt_tgt->server) != 2) return KRB5_KDCREP_MODIFIED; @@ -454,37 +448,21 @@ find_nxt_kdc(struct tr_state *ts) break; } } - if (*kdcptr != NULL) { - ts->nxt_kdc = kdcptr; - TR_DBG_RET(ts, "find_nxt_kdc", 0); - return 0; - } - - r2 = krb5_princ_component(ts->ctx, ts->kdc_list[0], 1); - if (r1 != NULL && r2 != NULL && data_eq(*r1, *r2)) { - TR_DBG_RET(ts, "find_nxt_kdc: looped back to local", - KRB5_KDCREP_MODIFIED); - return KRB5_KDCREP_MODIFIED; - } - - /* - * Realm is not in our list; we probably got an unexpected realm - * referral. - */ - ts->offpath_tgt = ts->nxt_tgt; - if (ts->cur_kdc == ts->kdc_list) { + if (*kdcptr == NULL) { /* - * Local KDC referred us off path; trust it for caching - * purposes. + * Not found; we probably got an unexpected realm referral. + * Don't touch NXT_KDC, thus allowing next_closest_tgt() to + * continue looping backwards. */ - return 0; + if (ts->ntgts > 0) { + /* Punt NXT_TGT from KDC_TGTS if bogus. */ + krb5_free_creds(ts->ctx, ts->kdc_tgts[--ts->ntgts]); + ts->kdc_tgts[ts->ntgts] = NULL; + } + TR_DBG_RET(ts, "find_nxt_kdc", KRB5_KDCREP_MODIFIED); + return KRB5_KDCREP_MODIFIED; } - /* - * Unlink the off-path TGT from KDC_TGTS but don't free it, - * because we should return it. - */ - ts->kdc_tgts[--ts->ntgts] = NULL; - ts->nxt_tgt = ts->cur_tgt; + ts->nxt_kdc = kdcptr; TR_DBG_RET(ts, "find_nxt_kdc", 0); return 0; } @@ -599,8 +577,10 @@ next_closest_tgt(struct tr_state *ts, krb5_principal client) break; } /* - * In case of errors in try_kdc() or find_nxt_kdc(), continue - * looping through the KDC list. + * Because try_kdc() validates referral TGTs, it can return an + * error indicating a bogus referral. The loop continues when + * it gets a bogus referral, which is arguably the right + * thing. (Previous implementation unconditionally failed.) */ } /* @@ -709,8 +689,7 @@ do_traversal(krb5_context ctx, krb5_principal server, krb5_creds *out_cc_tgt, krb5_creds **out_tgt, - krb5_creds ***out_kdc_tgts, - int *tgtptr_isoffpath) + krb5_creds ***out_kdc_tgts) { krb5_error_code retval; struct tr_state state, *ts; @@ -738,23 +717,13 @@ do_traversal(krb5_context ctx, retval = next_closest_tgt(ts, client); if (retval) goto cleanup; - - if (ts->offpath_tgt != NULL) { - retval = chase_offpath(ts, client, server); - if (retval) - goto cleanup; - break; - } assert(ts->cur_kdc != ts->nxt_kdc); } if (NXT_TGT_IS_CACHED(ts)) { - assert(ts->offpath_tgt = NULL); *out_cc_tgt = *ts->cur_cc_tgt; *out_tgt = out_cc_tgt; MARK_CUR_CC_TGT_CLEAN(ts); - } else if (ts->offpath_tgt != NULL){ - *out_tgt = ts->offpath_tgt; } else { /* CUR_TGT is somewhere in KDC_TGTS; no need to copy. */ *out_tgt = ts->nxt_tgt; @@ -770,121 +739,9 @@ cleanup: free(ts->kdc_tgts); } else *out_kdc_tgts = ts->kdc_tgts; - *tgtptr_isoffpath = (ts->offpath_tgt != NULL); - return retval; -} - -/* - * chase_offpath() - * - * Chase off-path TGT referrals. - * - * If we are traversing a trusted path (either hierarchically derived - * or explicit capath) and get a TGT pointing to a realm off this - * path, query the realm referenced by that off-path TGT. Repeat - * until we get to the destination realm or encounter an error. - */ -static krb5_error_code -chase_offpath(struct tr_state *ts, - krb5_principal client, krb5_principal server) -{ - krb5_error_code retval; - krb5_creds mcred; - krb5_creds *cur_tgt, *nxt_tgt, *reftgts[KRB5_REFERRAL_MAXHOPS]; - krb5_data *rsrc, *rdst, *r1; - int rcount, i; - - rdst = krb5_princ_realm(ts->ctx, server); - cur_tgt = ts->offpath_tgt; - ts->offpath_tgt = NULL; - - for (rcount = 0; rcount < KRB5_REFERRAL_MAXHOPS; rcount++) { - nxt_tgt = NULL; - memset(&mcred, 0, sizeof(mcred)); - rsrc = krb5_princ_component(ts->ctx, cur_tgt->server, 1); - retval = krb5_tgtname(ts->ctx, rdst, rsrc, &mcred.server); - if (retval) - goto cleanup; - mcred.client = client; - retval = krb5_get_cred_via_tkt(ts->ctx, cur_tgt, - FLAGS2OPTS(cur_tgt->ticket_flags), - cur_tgt->addresses, &mcred, &nxt_tgt); - mcred.client = NULL; - krb5_free_principal(ts->ctx, mcred.server); - mcred.server = NULL; - if (retval) - goto cleanup; - if (!IS_TGS_PRINC(ts->ctx, nxt_tgt->server)) { - krb5_free_creds(ts->ctx, nxt_tgt); - retval = KRB5_KDCREP_MODIFIED; - goto cleanup; - } - r1 = krb5_princ_component(ts->ctx, nxt_tgt->server, 1); - if (data_eq(*rdst, *r1)) { - retval = 0; - goto cleanup; - } - /* Don't free CUR_TGT if it's in list of TGTs to cache. */ - if (cur_tgt != ts->nxt_tgt) { - krb5_free_creds(ts->ctx, cur_tgt); - } - retval = offpath_loopchk(ts, nxt_tgt, reftgts, rcount); - if (retval) - goto cleanup; - reftgts[rcount] = nxt_tgt; - cur_tgt = nxt_tgt; - nxt_tgt = NULL; - } - /* Max hop count exceeded. */ - retval = KRB5_KDCREP_MODIFIED; - -cleanup: - if (mcred.server != NULL) { - krb5_free_principal(ts->ctx, mcred.server); - } - /* Don't free CUR_TGT if it's in list of TGTs to cache. */ - if (cur_tgt != ts->nxt_tgt && rcount && cur_tgt != reftgts[rcount-1]) { - krb5_free_creds(ts->ctx, cur_tgt); - } - if (nxt_tgt != NULL) { - if (retval) - krb5_free_creds(ts->ctx, nxt_tgt); - else - ts->offpath_tgt = nxt_tgt; - } - for (i = 0; i < rcount; i++) { - krb5_free_creds(ts->ctx, reftgts[i]); - } return retval; } -/* - * offpath_loopchk() - * - * Check for loop back to previously-visited realms, both off-path and - * on-path. - */ -static krb5_error_code -offpath_loopchk(struct tr_state *ts, - krb5_creds *tgt, krb5_creds *reftgts[], int rcount) -{ - krb5_data *r1, *r2; - int i; - - r1 = krb5_princ_component(ts->ctx, tgt->server, 1); - for (i = 0; i < rcount; i++) { - r2 = krb5_princ_component(ts->ctx, reftgts[i]->server, 1); - if (data_eq(*r1, *r2)) - return KRB5_KDCREP_MODIFIED; - } - for (i = 0; i < ts->ntgts; i++) { - r2 = krb5_princ_component(ts->ctx, ts->kdc_tgts[i]->server, 1); - if (data_eq(*r1, *r2)) - return KRB5_KDCREP_MODIFIED; - } - return 0; -} - /* * krb5_get_cred_from_kdc_opt() * krb5_get_cred_from_kdc() @@ -929,8 +786,6 @@ krb5_get_cred_from_kdc_opt(krb5_context context, krb5_ccache ccache, krb5_error_code retval, subretval; krb5_principal client, server, supplied_server, out_supplied_server; krb5_creds tgtq, cc_tgt, *tgtptr, *referral_tgts[KRB5_REFERRAL_MAXHOPS]; - krb5_creds *otgtptr = NULL; - int tgtptr_isoffpath = 0; krb5_boolean old_use_conf_ktypes; char **hrealms; int referral_count, i; @@ -992,10 +847,8 @@ krb5_get_cred_from_kdc_opt(krb5_context context, krb5_ccache ccache, } else if (!HARD_CC_ERR(retval)) { DPRINTF(("gc_from_kdc: starting do_traversal to find " "initial TGT for referral\n")); - tgtptr_isoffpath = 0; - otgtptr = NULL; retval = do_traversal(context, ccache, client, server, - &cc_tgt, &tgtptr, tgts, &tgtptr_isoffpath); + &cc_tgt, &tgtptr, tgts); } if (retval) { DPRINTF(("gc_from_kdc: failed to find initial TGT for referral\n")); @@ -1010,11 +863,6 @@ krb5_get_cred_from_kdc_opt(krb5_context context, krb5_ccache ccache, * path, otherwise fall back to old-style assumptions. */ - /* - * Save TGTPTR because we rewrite it in the referral loop, and - * we might need to explicitly free it later. - */ - otgtptr = tgtptr; for (referral_count = 0; referral_count < KRB5_REFERRAL_MAXHOPS; referral_count++) { @@ -1213,11 +1061,6 @@ krb5_get_cred_from_kdc_opt(krb5_context context, krb5_ccache ccache, /* Free tgtptr data if reused from above. */ if (tgtptr == &cc_tgt) krb5_free_cred_contents(context, tgtptr); - tgtptr = NULL; - /* Free saved TGT in OTGTPTR if it was off-path. */ - if (tgtptr_isoffpath) - krb5_free_creds(context, otgtptr); - otgtptr = NULL; /* Free TGTS if previously filled by do_traversal() */ if (*tgts != NULL) { for (i = 0; (*tgts)[i] != NULL; i++) { @@ -1232,13 +1075,11 @@ krb5_get_cred_from_kdc_opt(krb5_context context, krb5_ccache ccache, if (!retval) { tgtptr = &cc_tgt; } else if (!HARD_CC_ERR(retval)) { - tgtptr_isoffpath = 0; retval = do_traversal(context, ccache, client, server, - &cc_tgt, &tgtptr, tgts, &tgtptr_isoffpath); + &cc_tgt, &tgtptr, tgts); } if (retval) goto cleanup; - otgtptr = tgtptr; /* * Finally have TGT for target realm! Try using it to get creds. @@ -1261,8 +1102,6 @@ cleanup: krb5_free_cred_contents(context, &tgtq); if (tgtptr == &cc_tgt) krb5_free_cred_contents(context, tgtptr); - if (tgtptr_isoffpath) - krb5_free_creds(context, otgtptr); context->use_conf_ktypes = old_use_conf_ktypes; /* Drop the original principal back into in_cred so that it's cached in the expected format. */ -- cgit