home | help | back | first | fref | pref | prev | next | nref | lref | last | post |
Date: Tue, 29 Apr 2014 16:42:33 -0400 From: Tom Yu <tlyu@mit.edu> Message-Id: <201404292042.s3TKgX6A023468@drugstore.mit.edu> To: cvs-krb5@mit.edu Reply-To: krbdev@mit.edu MIME-Version: 1.0 Content-Type: text/plain; charset="us-ascii" Content-Transfer-Encoding: 7bit Errors-To: cvs-krb5-bounces@mit.edu https://github.com/krb5/krb5/commit/4d08c9abfee0b5978d9db2280c10c85b3bf2ae11 commit 4d08c9abfee0b5978d9db2280c10c85b3bf2ae11 Author: Tom Yu <tlyu@mit.edu> Date: Thu Apr 24 17:10:58 2014 -0400 Refactor KDC option/flag processing A lot of KDC code was spent copying options to flags, and copying header_ticket flags to the output ticket. Behavior change: previous code didn't copy PROXY from the header_ticket, but this seems to have been a minor bug rather than intentional. This also seems to have been an omission from RFC 4120. src/kdc/do_as_req.c | 18 +++---------- src/kdc/do_tgs_req.c | 46 ++++++++------------------------- src/kdc/kdc_util.h | 68 +++++++++++++++++++++++++++++++++++++++++++++++++- 3 files changed, 82 insertions(+), 50 deletions(-) diff --git a/src/kdc/do_as_req.c b/src/kdc/do_as_req.c index 5057067..a1db924 100644 --- a/src/kdc/do_as_req.c +++ b/src/kdc/do_as_req.c @@ -2,8 +2,8 @@ /* kdc/do_as_req.c */ /* * Portions Copyright (C) 2007 Apple Inc. - * Copyright 1990, 1991, 2007, 2008, 2009, 2013 by the Massachusetts Institute - * of Technology. All Rights Reserved. + * Copyright 1990, 1991, 2007, 2008, 2009, 2013, 2014 by the + * Massachusetts Institute of Technology. All Rights Reserved. * * Export of this software from the United States of America may * require a specific license from the United States Government. @@ -686,7 +686,8 @@ process_as_req(krb5_kdc_req *request, krb5_data *req_pkt, state->ticket_reply.server = state->request->server; } - state->enc_tkt_reply.flags = 0; + /* Copy options that request the corresponding ticket flags. */ + state->enc_tkt_reply.flags = OPTS2FLAGS(state->request->kdc_options); state->enc_tkt_reply.times.authtime = state->authtime; setflag(state->enc_tkt_reply.flags, TKT_FLG_INITIAL); @@ -698,15 +699,6 @@ process_as_req(krb5_kdc_req *request, krb5_data *req_pkt, * realms may refuse to issue renewable tickets */ - if (isflagset(state->request->kdc_options, KDC_OPT_FORWARDABLE)) - setflag(state->enc_tkt_reply.flags, TKT_FLG_FORWARDABLE); - - if (isflagset(state->request->kdc_options, KDC_OPT_PROXIABLE)) - setflag(state->enc_tkt_reply.flags, TKT_FLG_PROXIABLE); - - if (isflagset(state->request->kdc_options, KDC_OPT_ALLOW_POSTDATE)) - setflag(state->enc_tkt_reply.flags, TKT_FLG_MAY_POSTDATE); - state->enc_tkt_reply.session = &state->session_key; if (isflagset(state->c_flags, KRB5_KDB_FLAG_CANONICALIZE)) { state->client_princ = *(state->client->princ); @@ -720,7 +712,6 @@ process_as_req(krb5_kdc_req *request, krb5_data *req_pkt, state->enc_tkt_reply.transited.tr_contents = empty_string; if (isflagset(state->request->kdc_options, KDC_OPT_POSTDATED)) { - setflag(state->enc_tkt_reply.flags, TKT_FLG_POSTDATED); setflag(state->enc_tkt_reply.flags, TKT_FLG_INVALID); state->enc_tkt_reply.times.starttime = state->request->from; } else @@ -757,7 +748,6 @@ process_as_req(krb5_kdc_req *request, krb5_data *req_pkt, state->status = "VALIDATE_ANONYMOUS_PRINCIPAL"; goto errout; } - setflag(state->enc_tkt_reply.flags, TKT_FLG_ANONYMOUS); krb5_free_principal(kdc_context, state->request->client); state->request->client = NULL; errcode = krb5_copy_principal(kdc_context, krb5_anonymous_principal(), diff --git a/src/kdc/do_tgs_req.c b/src/kdc/do_tgs_req.c index 49a6ea6..fce478e 100644 --- a/src/kdc/do_tgs_req.c +++ b/src/kdc/do_tgs_req.c @@ -1,8 +1,8 @@ /* -*- mode: c; c-basic-offset: 4; indent-tabs-mode: nil -*- */ /* kdc/do_tgs_req.c - KDC Routines to deal with TGS_REQ's */ /* - * Copyright 1990, 1991, 2001, 2007, 2008, 2009, 2013 by the Massachusetts - * Institute of Technology. All Rights Reserved. + * Copyright 1990, 1991, 2001, 2007, 2008, 2009, 2013, 2014 by the + * Massachusetts Institute of Technology. All Rights Reserved. * * Export of this software from the United States of America may * require a specific license from the United States Government. @@ -376,7 +376,8 @@ process_tgs_req(struct server_handle *handle, krb5_data *pkt, else ticket_reply.server = request->server; /* XXX careful for realm... */ - enc_tkt_reply.flags = 0; + enc_tkt_reply.flags = OPTS2FLAGS(request->kdc_options); + enc_tkt_reply.flags |= COPY_TKT_FLAGS(header_enc_tkt->flags); enc_tkt_reply.times.starttime = 0; if (isflagset(server->attributes, KRB5_KDB_OK_AS_DELEGATE)) @@ -404,7 +405,6 @@ process_tgs_req(struct server_handle *handle, krb5_data *pkt, */ if (isflagset(request->kdc_options, KDC_OPT_FORWARDABLE)) { - setflag(enc_tkt_reply.flags, TKT_FLG_FORWARDABLE); if (isflagset(c_flags, KRB5_KDB_FLAG_PROTOCOL_TRANSITION)) { /* @@ -435,34 +435,21 @@ process_tgs_req(struct server_handle *handle, krb5_data *pkt, } } - if (isflagset(request->kdc_options, KDC_OPT_FORWARDED)) { - setflag(enc_tkt_reply.flags, TKT_FLG_FORWARDED); + if (isflagset(request->kdc_options, KDC_OPT_FORWARDED) || + isflagset(request->kdc_options, KDC_OPT_PROXY)) { /* include new addresses in ticket & reply */ enc_tkt_reply.caddrs = request->addresses; reply_encpart.caddrs = request->addresses; } - if (isflagset(header_enc_tkt->flags, TKT_FLG_FORWARDED)) - setflag(enc_tkt_reply.flags, TKT_FLG_FORWARDED); - - if (isflagset(request->kdc_options, KDC_OPT_PROXIABLE)) - setflag(enc_tkt_reply.flags, TKT_FLG_PROXIABLE); - - if (isflagset(request->kdc_options, KDC_OPT_PROXY)) { - setflag(enc_tkt_reply.flags, TKT_FLG_PROXY); - - /* include new addresses in ticket & reply */ - - enc_tkt_reply.caddrs = request->addresses; - reply_encpart.caddrs = request->addresses; - } - - if (isflagset(request->kdc_options, KDC_OPT_ALLOW_POSTDATE)) - setflag(enc_tkt_reply.flags, TKT_FLG_MAY_POSTDATE); + /* We don't currently handle issuing anonymous tickets based on + * non-anonymous ones, so just ignore the option. */ + if (isflagset(request->kdc_options, KDC_OPT_REQUEST_ANONYMOUS) && + !isflagset(header_enc_tkt->flags, TKT_FLG_ANONYMOUS)) + clear(enc_tkt_reply.flags, TKT_FLG_ANONYMOUS); if (isflagset(request->kdc_options, KDC_OPT_POSTDATED)) { - setflag(enc_tkt_reply.flags, TKT_FLG_POSTDATED); setflag(enc_tkt_reply.flags, TKT_FLG_INVALID); enc_tkt_reply.times.starttime = request->from; } else @@ -506,22 +493,11 @@ process_tgs_req(struct server_handle *handle, krb5_data *pkt, kdc_get_ticket_renewtime(kdc_active_realm, request, header_enc_tkt, client, server, &enc_tkt_reply); - if (isflagset(header_enc_tkt->flags, TKT_FLG_ANONYMOUS)) - setflag(enc_tkt_reply.flags, TKT_FLG_ANONYMOUS); /* * Set authtime to be the same as header or evidence ticket's */ enc_tkt_reply.times.authtime = authtime; - /* - * Propagate the preauthentication flags through to the returned ticket. - */ - if (isflagset(header_enc_tkt->flags, TKT_FLG_PRE_AUTH)) - setflag(enc_tkt_reply.flags, TKT_FLG_PRE_AUTH); - - if (isflagset(header_enc_tkt->flags, TKT_FLG_HW_AUTH)) - setflag(enc_tkt_reply.flags, TKT_FLG_HW_AUTH); - /* starttime is optional, and treated as authtime if not present. so we can nuke it if it matches */ if (enc_tkt_reply.times.starttime == enc_tkt_reply.times.authtime) diff --git a/src/kdc/kdc_util.h b/src/kdc/kdc_util.h index 6c54333..479a13c 100644 --- a/src/kdc/kdc_util.h +++ b/src/kdc/kdc_util.h @@ -2,7 +2,7 @@ /* kdc/kdc_util.h */ /* * Portions Copyright (C) 2007 Apple Inc. - * Copyright 1990, 2007 by the Massachusetts Institute of Technology. + * Copyright 1990, 2007, 2014 by the Massachusetts Institute of Technology. * * Export of this software from the United States of America may * require a specific license from the United States Government. @@ -414,6 +414,72 @@ struct krb5_kdcpreauth_rock_st { /* TGS-REQ options which are not compatible with referrals */ #define NO_REFERRAL_OPTION (NON_TGT_OPTION | KDC_OPT_ENC_TKT_IN_SKEY) +/* + * Mask of KDC options that request the corresponding ticket flag with + * the same number. Some of these are invalid for AS-REQs, but + * validate_as_request() takes care of that. KDC_OPT_RENEWABLE isn't + * here because it needs special handling in + * kdc_get_ticket_renewtime(). + * + * According to RFC 4120 section 3.1.3 the following AS-REQ options + * request their corresponding ticket flags if local policy allows: + * + * KDC_OPT_FORWARDABLE KDC_OPT_ALLOW_POSTDATE + * KDC_OPT_POSTDATED KDC_OPT_PROXIABLE + * KDC_OPT_RENEWABLE + * + * RFC 1510 section A.6 shows pseudocode indicating that the following + * TGS-REQ options request their corresponding ticket flags if local + * policy allows: + * + * KDC_OPT_FORWARDABLE KDC_OPT_FORWARDED + * KDC_OPT_PROXIABLE KDC_OPT_PROXY + * KDC_OPT_POSTDATED KDC_OPT_RENEWABLE + * + * The above list omits KDC_OPT_ALLOW_POSTDATE, but RFC 4120 section + * 5.4.1 says the TGS also handles it. + * + * RFC 6112 makes KDC_OPT_REQUEST_ANONYMOUS the same bit number as + * TKT_FLG_ANONYMOUS. + */ +#define OPTS_COMMON_FLAGS_MASK \ + (KDC_OPT_FORWARDABLE | KDC_OPT_FORWARDED | \ + KDC_OPT_PROXIABLE | KDC_OPT_PROXY | \ + KDC_OPT_ALLOW_POSTDATE | KDC_OPT_POSTDATED | \ + KDC_OPT_REQUEST_ANONYMOUS) + +/* Copy KDC options that request the corresponding ticket flags. */ +#define OPTS2FLAGS(x) (x & OPTS_COMMON_FLAGS_MASK) + +/* + * Mask of ticket flags for the TGS to propagate from a ticket to a + * derivative ticket. + * + * RFC 4120 section 2.1 says the following flags are carried forward + * from an initial ticket to derivative tickets: + * + * TKT_FLG_PRE_AUTH + * TKT_FLG_HW_AUTH + * + * RFC 4120 section 2.6 says TKT_FLG_FORWARDED is carried forward to + * derivative tickets. Proxy tickets are basically identical to + * forwarded tickets except that a TGT may never be proxied, therefore + * tickets derived from proxy tickets should have TKT_FLAG_PROXY set. + * RFC 4120 and RFC 1510 apparently have an accidental omission in not + * requiring that tickets derived from a proxy ticket have + * TKT_FLG_PROXY set. Previous code also omitted this behavior. + * + * RFC 6112 section 4.2 implies that TKT_FLG_ANONYMOUS must be + * propagated from an anonymous ticket to derivative tickets. + */ +#define TGS_COPIED_FLAGS_MASK \ + (TKT_FLG_FORWARDED | TKT_FLG_PROXY | \ + TKT_FLG_PRE_AUTH | TKT_FLG_HW_AUTH | \ + TKT_FLG_ANONYMOUS) + +/* Copy appropriate header ticket flags to new ticket. */ +#define COPY_TKT_FLAGS(x) (x & TGS_COPIED_FLAGS_MASK) + int check_anon(kdc_realm_t *kdc_active_realm, krb5_principal client, krb5_principal server); int errcode_to_protocol(krb5_error_code code); _______________________________________________ cvs-krb5 mailing list cvs-krb5@mit.edu https://mailman.mit.edu/mailman/listinfo/cvs-krb5
home | help | back | first | fref | pref | prev | next | nref | lref | last | post |