kdc: add accessor functions for KDC request structure
Add accessor functions for use by Samba and other plugin developers. Documentation is in kdc/kdc-accessors.h.
This commit is contained in:
@@ -133,6 +133,7 @@ CLEANFILES = \
|
||||
wind.h \
|
||||
wind_err.h \
|
||||
kdc-plugin.h \
|
||||
kdc-accessors.h \
|
||||
kdc-audit.h \
|
||||
csr_authorizer_plugin.h \
|
||||
gss_preauth_authorizer_plugin.h \
|
||||
|
@@ -244,7 +244,7 @@ include_HEADERS = kdc.h $(srcdir)/kdc-protos.h
|
||||
noinst_HEADERS = $(srcdir)/kdc-private.h
|
||||
|
||||
krb5dir = $(includedir)/krb5
|
||||
krb5_HEADERS = kdc-audit.h kdc-plugin.h token_validator_plugin.h csr_authorizer_plugin.h gss_preauth_authorizer_plugin.h
|
||||
krb5_HEADERS = kdc-audit.h kdc-plugin.h kdc-accessors.h token_validator_plugin.h csr_authorizer_plugin.h gss_preauth_authorizer_plugin.h
|
||||
|
||||
build_HEADERZ = $(krb5_HEADERS) # XXX
|
||||
|
||||
|
@@ -52,7 +52,8 @@ INCFILES=\
|
||||
$(INCDIR)\kdc-protos.h \
|
||||
$(INCDIR)\kdc-private.h \
|
||||
$(INCDIR)\krb5\kdc-audit.h \
|
||||
$(INCDIR)\krb5\kdc-plugin.h
|
||||
$(INCDIR)\krb5\kdc-plugin.h \
|
||||
$(INCDIR)\krb5\kdc-accessors.h
|
||||
|
||||
all:: $(INCFILES) $(LIBKDC) $(BINPROGRAMS) $(SBINPROGRAMS) $(LIBEXECPROGRAMS)
|
||||
|
||||
|
@@ -397,7 +397,10 @@ authorize(void *ctx,
|
||||
struct altsecid_gss_preauth_authorizer_context *c = ctx;
|
||||
struct ad_server_tuple *server = NULL;
|
||||
krb5_error_code ret;
|
||||
krb5_const_realm realm = krb5_principal_get_realm(r->context, r->client->principal);
|
||||
krb5_context context = kdc_request_get_context((kdc_request_t)r);
|
||||
const hdb_entry *client = kdc_request_get_client(r);
|
||||
krb5_const_principal server_princ = kdc_request_get_server_princ(r);
|
||||
krb5_const_realm realm = krb5_principal_get_realm(context, client->principal);
|
||||
krb5_boolean reconnect_p = FALSE;
|
||||
krb5_boolean is_tgs;
|
||||
heim_data_t requestor_sid = NULL;
|
||||
@@ -405,11 +408,11 @@ authorize(void *ctx,
|
||||
*authorized = FALSE;
|
||||
*mapped_name = NULL;
|
||||
|
||||
if (!krb5_principal_is_federated(r->context, r->client->principal) ||
|
||||
if (!krb5_principal_is_federated(context, client->principal) ||
|
||||
(ret_flags & GSS_C_ANON_FLAG))
|
||||
return KRB5_PLUGIN_NO_HANDLE;
|
||||
|
||||
is_tgs = krb5_principal_is_krbtgt(r->context, r->server_princ);
|
||||
is_tgs = krb5_principal_is_krbtgt(context, server_princ);
|
||||
|
||||
HEIM_TAILQ_FOREACH(server, &c->servers, link) {
|
||||
if (strcmp(realm, server->realm) == 0)
|
||||
@@ -419,12 +422,12 @@ authorize(void *ctx,
|
||||
if (server == NULL) {
|
||||
server = calloc(1, sizeof(*server));
|
||||
if (server == NULL)
|
||||
return krb5_enomem(r->context);
|
||||
return krb5_enomem(context);
|
||||
|
||||
server->realm = strdup(realm);
|
||||
if (server->realm == NULL) {
|
||||
free(server);
|
||||
return krb5_enomem(r->context);
|
||||
return krb5_enomem(context);
|
||||
}
|
||||
|
||||
HEIM_TAILQ_INSERT_HEAD(&c->servers, server, link);
|
||||
@@ -432,12 +435,12 @@ authorize(void *ctx,
|
||||
|
||||
do {
|
||||
if (server->ld == NULL) {
|
||||
ret = ad_connect(r->context, realm, server);
|
||||
ret = ad_connect(context, realm, server);
|
||||
if (ret)
|
||||
return ret;
|
||||
}
|
||||
|
||||
ret = ad_lookup(r->context, realm, server,
|
||||
ret = ad_lookup(context, realm, server,
|
||||
initiator_name, mech_type,
|
||||
mapped_name, is_tgs ? &requestor_sid : NULL);
|
||||
if (ret == KRB5KDC_ERR_SVC_UNAVAILABLE) {
|
||||
@@ -472,8 +475,8 @@ finalize_pac(void *ctx, astgs_request_t r)
|
||||
|
||||
kdc_audit_setkv_object((kdc_request_t)r, "gss_requestor_sid", requestor_sid);
|
||||
|
||||
return krb5_pac_add_buffer(r->context, r->pac, PAC_REQUESTOR_SID,
|
||||
heim_data_get_data(requestor_sid));
|
||||
return kdc_request_add_pac_buffer(r, PAC_REQUESTOR_SID,
|
||||
heim_data_get_data(requestor_sid));
|
||||
}
|
||||
|
||||
static KRB5_LIB_CALL krb5_error_code
|
||||
|
349
kdc/kdc-accessors.h
Normal file
349
kdc/kdc-accessors.h
Normal file
@@ -0,0 +1,349 @@
|
||||
/*
|
||||
* Copyright (c) 2022, PADL Software Pty Ltd.
|
||||
* All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
*
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
*
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
*
|
||||
* 3. Neither the name of PADL Software nor the names of its contributors
|
||||
* may be used to endorse or promote products derived from this software
|
||||
* without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY PADL SOFTWARE AND CONTRIBUTORS ``AS IS'' AND
|
||||
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL PADL SOFTWARE OR CONTRIBUTORS BE LIABLE
|
||||
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
||||
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*/
|
||||
|
||||
#ifndef HEIMDAL_KDC_KDC_ACCESSORS_H
|
||||
#define HEIMDAL_KDC_KDC_ACCESSORS_H 1
|
||||
|
||||
/* read-only accessor */
|
||||
#ifndef _KDC_REQUEST_GET_ACCESSOR
|
||||
#define _KDC_REQUEST_GET_ACCESSOR(R, T, f) \
|
||||
T \
|
||||
kdc_request_get_ ## f(R);
|
||||
#endif
|
||||
|
||||
#ifndef _KDC_REQUEST_SET_ACCESSOR
|
||||
#define _KDC_REQUEST_SET_ACCESSOR(R, T, f) \
|
||||
void \
|
||||
kdc_request_set_ ## f(R, T);
|
||||
#endif
|
||||
|
||||
#ifndef KDC_REQUEST_GET_ACCESSOR
|
||||
#define KDC_REQUEST_GET_ACCESSOR(T, f) \
|
||||
_KDC_REQUEST_GET_ACCESSOR(kdc_request_t, T, f)
|
||||
#endif
|
||||
|
||||
#ifndef KDC_REQUEST_SET_ACCESSOR
|
||||
#define KDC_REQUEST_SET_ACCESSOR(T, f) \
|
||||
_KDC_REQUEST_SET_ACCESSOR(kdc_request_t, T, f)
|
||||
#endif
|
||||
|
||||
#ifndef ASTGS_REQUEST_GET_ACCESSOR
|
||||
#define ASTGS_REQUEST_GET_ACCESSOR(T, f) \
|
||||
_KDC_REQUEST_GET_ACCESSOR(astgs_request_t, T, f)
|
||||
#endif
|
||||
|
||||
#ifndef ASTGS_REQUEST_SET_ACCESSOR
|
||||
#define ASTGS_REQUEST_SET_ACCESSOR(T, f) \
|
||||
_KDC_REQUEST_SET_ACCESSOR(astgs_request_t, T, f)
|
||||
#endif
|
||||
|
||||
/* get/set accessor for pointer type */
|
||||
#ifndef _KDC_REQUEST_GET_ACCESSOR_PTR
|
||||
#define _KDC_REQUEST_GET_ACCESSOR_PTR(R, T, f) \
|
||||
const T \
|
||||
kdc_request_get_ ## f(R);
|
||||
#endif
|
||||
|
||||
#ifndef _KDC_REQUEST_SET_ACCESSOR_PTR
|
||||
#define _KDC_REQUEST_SET_ACCESSOR_PTR(R, T, t, f) \
|
||||
krb5_error_code \
|
||||
kdc_request_set_ ## f(R, const T);
|
||||
#endif
|
||||
|
||||
#ifndef KDC_REQUEST_GET_ACCESSOR_PTR
|
||||
#define KDC_REQUEST_GET_ACCESSOR_PTR(T, f) \
|
||||
_KDC_REQUEST_GET_ACCESSOR_PTR(kdc_request_t, T, f)
|
||||
#endif
|
||||
|
||||
#ifndef KDC_REQUEST_SET_ACCESSOR_PTR
|
||||
#define KDC_REQUEST_SET_ACCESSOR_PTR(T, t, f) \
|
||||
_KDC_REQUEST_SET_ACCESSOR_PTR(kdc_request_t, T, t, f)
|
||||
#endif
|
||||
|
||||
#ifndef ASTGS_REQUEST_GET_ACCESSOR_PTR
|
||||
#define ASTGS_REQUEST_GET_ACCESSOR_PTR(T, f) \
|
||||
_KDC_REQUEST_GET_ACCESSOR_PTR(astgs_request_t, T, f)
|
||||
#endif
|
||||
|
||||
#ifndef ASTGS_REQUEST_SET_ACCESSOR_PTR
|
||||
#define ASTGS_REQUEST_SET_ACCESSOR_PTR(T, t, f) \
|
||||
_KDC_REQUEST_SET_ACCESSOR_PTR(astgs_request_t, T, t, f)
|
||||
#endif
|
||||
|
||||
/* get/set accessor for struct type */
|
||||
#ifndef _KDC_REQUEST_GET_ACCESSOR_STRUCT
|
||||
#define _KDC_REQUEST_GET_ACCESSOR_STRUCT(R, T, f) \
|
||||
const T * \
|
||||
kdc_request_get_ ## f(R);
|
||||
#endif
|
||||
|
||||
#ifndef _KDC_REQUEST_SET_ACCESSOR_STRUCT
|
||||
#define _KDC_REQUEST_SET_ACCESSOR_STRUCT(R, T, t, f) \
|
||||
krb5_error_code \
|
||||
kdc_request_set_ ## f(R, const T *);
|
||||
#endif
|
||||
|
||||
#ifndef KDC_REQUEST_GET_ACCESSOR_STRUCT
|
||||
#define KDC_REQUEST_GET_ACCESSOR_STRUCT(T, f) \
|
||||
_KDC_REQUEST_GET_ACCESSOR_STRUCT(kdc_request_t, T, f)
|
||||
#endif
|
||||
|
||||
#ifndef KDC_REQUEST_SET_ACCESSOR_STRUCT
|
||||
#define KDC_REQUEST_SET_ACCESSOR_STRUCT(T, t, f) \
|
||||
_KDC_REQUEST_SET_ACCESSOR_STRUCT(kdc_request_t, T, t, f)
|
||||
#endif
|
||||
|
||||
#ifndef ASTGS_REQUEST_GET_ACCESSOR_STRUCT
|
||||
#define ASTGS_REQUEST_GET_ACCESSOR_STRUCT(T, f) \
|
||||
_KDC_REQUEST_GET_ACCESSOR_STRUCT(astgs_request_t, T, f)
|
||||
#endif
|
||||
|
||||
#ifndef ASTGS_REQUEST_SET_ACCESSOR_STRUCT
|
||||
#define ASTGS_REQUEST_SET_ACCESSOR_STRUCT(T, t, f) \
|
||||
_KDC_REQUEST_SET_ACCESSOR_STRUCT(astgs_request_t, T, t, f)
|
||||
#endif
|
||||
|
||||
/*
|
||||
* krb5_context
|
||||
* kdc_request_get_context(kdc_request_t);
|
||||
*/
|
||||
|
||||
KDC_REQUEST_GET_ACCESSOR(krb5_context, context)
|
||||
|
||||
/*
|
||||
* krb5_kdc_configuration *
|
||||
* kdc_request_get_config(kdc_request_t);
|
||||
*/
|
||||
|
||||
KDC_REQUEST_GET_ACCESSOR(krb5_kdc_configuration *, config)
|
||||
|
||||
/*
|
||||
* heim_log_facility *
|
||||
* kdc_request_get_logf(kdc_request_t);
|
||||
*/
|
||||
|
||||
KDC_REQUEST_GET_ACCESSOR(heim_log_facility *, logf)
|
||||
|
||||
/*
|
||||
* const char *
|
||||
* kdc_request_get_from(kdc_request_t);
|
||||
*/
|
||||
|
||||
KDC_REQUEST_GET_ACCESSOR_PTR(char *, from)
|
||||
|
||||
/*
|
||||
* const struct sockaddr *
|
||||
* kdc_request_get_addr(kdc_request_t);
|
||||
*/
|
||||
|
||||
KDC_REQUEST_GET_ACCESSOR_PTR(struct sockaddr *, addr)
|
||||
|
||||
/*
|
||||
* krb5_data
|
||||
* kdc_request_get_request(kdc_request_t);
|
||||
*/
|
||||
|
||||
KDC_REQUEST_GET_ACCESSOR(krb5_data, request)
|
||||
|
||||
/*
|
||||
* struct timeval
|
||||
* kdc_request_get_tv_start(kdc_request_t);
|
||||
*/
|
||||
|
||||
KDC_REQUEST_GET_ACCESSOR(struct timeval, tv_start)
|
||||
|
||||
/*
|
||||
* struct timeval
|
||||
* kdc_request_get_tv_end(kdc_request_t);
|
||||
*/
|
||||
|
||||
KDC_REQUEST_GET_ACCESSOR(struct timeval, tv_end)
|
||||
|
||||
/*
|
||||
* krb5_error_code
|
||||
* kdc_request_get_error_code(kdc_request_t);
|
||||
*/
|
||||
KDC_REQUEST_GET_ACCESSOR(krb5_error_code, error_code)
|
||||
|
||||
/*
|
||||
* void
|
||||
* kdc_request_set_error_code(kdc_request_t, krb5_error_code);
|
||||
*/
|
||||
KDC_REQUEST_SET_ACCESSOR(krb5_error_code, error_code)
|
||||
|
||||
/*
|
||||
* const KDC_REQ *
|
||||
* kdc_request_get_req(astgs_request_t);
|
||||
*/
|
||||
|
||||
ASTGS_REQUEST_GET_ACCESSOR_STRUCT(KDC_REQ, req)
|
||||
|
||||
/*
|
||||
* const KDC_REP *
|
||||
* kdc_request_get_rep(astgs_request_t);
|
||||
*/
|
||||
|
||||
ASTGS_REQUEST_GET_ACCESSOR_STRUCT(KDC_REP, rep)
|
||||
|
||||
/*
|
||||
* krb5_error_code
|
||||
* kdc_request_set_rep(astgs_request_t, const KDC_REP *);
|
||||
*/
|
||||
|
||||
ASTGS_REQUEST_SET_ACCESSOR_STRUCT(KDC_REP, KDC_REP, rep)
|
||||
|
||||
/*
|
||||
* const char *
|
||||
* kdc_request_get_cname(kdc_request_t);
|
||||
*/
|
||||
|
||||
KDC_REQUEST_GET_ACCESSOR_PTR(char *, cname)
|
||||
|
||||
/*
|
||||
* krb5_error_code
|
||||
* kdc_request_set_cname(kdc_request_t, const char *);
|
||||
*/
|
||||
|
||||
KDC_REQUEST_SET_ACCESSOR_PTR(char *, string_ptr, cname)
|
||||
|
||||
/*
|
||||
* const Principal *
|
||||
* kdc_request_get_client_princ(astgs_request_t);
|
||||
*/
|
||||
|
||||
ASTGS_REQUEST_GET_ACCESSOR_PTR(Principal *, client_princ)
|
||||
|
||||
/*
|
||||
* krb5_error_code
|
||||
* kdc_request_set_client_princ(astgs_request_t, const Principal *);
|
||||
*/
|
||||
|
||||
ASTGS_REQUEST_SET_ACCESSOR_PTR(Principal *, Principal_ptr, client_princ)
|
||||
|
||||
/*
|
||||
* const Principal *
|
||||
* kdc_request_get_canon_client_princ(astgs_request_t);
|
||||
*/
|
||||
|
||||
ASTGS_REQUEST_GET_ACCESSOR_PTR(Principal *, canon_client_princ)
|
||||
|
||||
/*
|
||||
* krb5_error_code
|
||||
* kdc_request_set_canon_client_princ(astgs_request_t, const Principal *);
|
||||
*/
|
||||
|
||||
ASTGS_REQUEST_SET_ACCESSOR_PTR(Principal *, Principal_ptr, canon_client_princ)
|
||||
|
||||
/*
|
||||
* const HDB *
|
||||
* kdc_request_get_clientdb(astgs_request_t);
|
||||
*/
|
||||
|
||||
ASTGS_REQUEST_GET_ACCESSOR_PTR(HDB *, clientdb)
|
||||
|
||||
/*
|
||||
* const hdb_entry *
|
||||
* kdc_request_get_client(astgs_request_t);
|
||||
*/
|
||||
|
||||
ASTGS_REQUEST_GET_ACCESSOR_PTR(hdb_entry *, client)
|
||||
|
||||
/*
|
||||
* See client accessors
|
||||
*/
|
||||
|
||||
KDC_REQUEST_GET_ACCESSOR_PTR(char *, sname)
|
||||
KDC_REQUEST_SET_ACCESSOR_PTR(char *, string_ptr, sname)
|
||||
ASTGS_REQUEST_GET_ACCESSOR_PTR(Principal *, server_princ)
|
||||
ASTGS_REQUEST_SET_ACCESSOR_PTR(Principal *, Principal_ptr, server_princ)
|
||||
ASTGS_REQUEST_GET_ACCESSOR_PTR(HDB *, serverdb)
|
||||
ASTGS_REQUEST_GET_ACCESSOR_PTR(hdb_entry *, server)
|
||||
|
||||
/*
|
||||
* See client accessors
|
||||
*/
|
||||
|
||||
ASTGS_REQUEST_GET_ACCESSOR_PTR(Principal *, krbtgt_princ)
|
||||
ASTGS_REQUEST_SET_ACCESSOR_PTR(Principal *, Principal_ptr, krbtgt_princ)
|
||||
ASTGS_REQUEST_GET_ACCESSOR_PTR(HDB *, krbtgtdb)
|
||||
ASTGS_REQUEST_GET_ACCESSOR_PTR(hdb_entry *, krbtgt)
|
||||
|
||||
/*
|
||||
* krb5_ticket *
|
||||
* kdc_request_get_ticket(astgs_request_t);
|
||||
*/
|
||||
|
||||
ASTGS_REQUEST_GET_ACCESSOR(krb5_ticket *, ticket)
|
||||
|
||||
/*
|
||||
* const krb5_keyblock *
|
||||
* kdc_request_get_reply_key(astgs_request_t);
|
||||
*/
|
||||
|
||||
ASTGS_REQUEST_GET_ACCESSOR_STRUCT(krb5_keyblock, reply_key)
|
||||
|
||||
/*
|
||||
* krb5_error_code
|
||||
* kdc_request_set_reply_key(astgs_request_t, const krb5_keyblock *);
|
||||
*/
|
||||
|
||||
ASTGS_REQUEST_SET_ACCESSOR_STRUCT(krb5_keyblock, keyblock, reply_key)
|
||||
|
||||
/*
|
||||
* krb5_const_pac
|
||||
* kdc_request_get_pac(astgs_request_t);
|
||||
*/
|
||||
|
||||
ASTGS_REQUEST_GET_ACCESSOR_PTR(struct krb5_pac_data *, pac)
|
||||
|
||||
/*
|
||||
* krb5_error_code
|
||||
* kdc_request_set_pac(astgs_request_t, krb5_const_pac);
|
||||
*/
|
||||
|
||||
ASTGS_REQUEST_SET_ACCESSOR_PTR(struct krb5_pac_data *, pac, pac)
|
||||
|
||||
/*
|
||||
* uint64_t
|
||||
* kdc_request_get_pac_attributes(astgs_request_t);
|
||||
*/
|
||||
|
||||
ASTGS_REQUEST_GET_ACCESSOR(uint64_t, pac_attributes)
|
||||
|
||||
/*
|
||||
* void
|
||||
* kdc_request_set_pac_attributes(astgs_request_t, uint64_t);
|
||||
*/
|
||||
|
||||
ASTGS_REQUEST_SET_ACCESSOR(uint64_t, pac_attributes)
|
||||
|
||||
#endif /* HEIMDAL_KDC_KDC_ACCESSORS_H */
|
188
kdc/kdc-plugin.c
188
kdc/kdc-plugin.c
@@ -3,6 +3,8 @@
|
||||
* (Royal Institute of Technology, Stockholm, Sweden).
|
||||
* All rights reserved.
|
||||
*
|
||||
* Portions (c) 2021, 2022 PADL Software Pty Ltd.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
@@ -305,3 +307,189 @@ kdc_get_instance(const char *libname)
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/*
|
||||
* Plugin accessors
|
||||
*/
|
||||
|
||||
krb5_error_code
|
||||
kdc_request_add_reply_padata(astgs_request_t r, PA_DATA *md)
|
||||
{
|
||||
heim_assert(r->rep.padata != NULL, "reply padata not allocated");
|
||||
return add_METHOD_DATA(r->rep.padata, md);
|
||||
}
|
||||
|
||||
krb5_error_code
|
||||
kdc_request_add_pac_buffer(astgs_request_t r, int32_t pactype, const krb5_data *d)
|
||||
{
|
||||
krb5_error_code ret;
|
||||
krb5_pac pac;
|
||||
|
||||
if (r->pac == NULL) {
|
||||
ret = krb5_pac_init(r->context, &pac);
|
||||
if (ret)
|
||||
return ret;
|
||||
} else
|
||||
pac = heim_retain(r->pac);
|
||||
|
||||
ret = krb5_pac_add_buffer(r->context, pac, pactype, d);
|
||||
if (ret == 0 && r->pac == NULL)
|
||||
r->pac = pac;
|
||||
else
|
||||
heim_release(pac);
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
#undef _KDC_REQUEST_GET_ACCESSOR
|
||||
#define _KDC_REQUEST_GET_ACCESSOR(R, T, f) \
|
||||
T \
|
||||
kdc_request_get_ ## f(R r) \
|
||||
{ \
|
||||
return r->f; \
|
||||
}
|
||||
|
||||
#undef _KDC_REQUEST_SET_ACCESSOR
|
||||
#define _KDC_REQUEST_SET_ACCESSOR(R, T, f) \
|
||||
void \
|
||||
kdc_request_set_ ## f(R r, T v) \
|
||||
{ \
|
||||
r->f = v; \
|
||||
}
|
||||
|
||||
#undef _KDC_REQUEST_GET_ACCESSOR_PTR
|
||||
#define _KDC_REQUEST_GET_ACCESSOR_PTR(R, T, f) \
|
||||
const T \
|
||||
kdc_request_get_ ## f(R r) \
|
||||
{ \
|
||||
return r->f; \
|
||||
}
|
||||
|
||||
#undef _KDC_REQUEST_SET_ACCESSOR_PTR
|
||||
#define _KDC_REQUEST_SET_ACCESSOR_PTR(R, T, t, f) \
|
||||
krb5_error_code \
|
||||
kdc_request_set_ ## f(R r, const T v) \
|
||||
{ \
|
||||
krb5_error_code ret; \
|
||||
T tmp; \
|
||||
\
|
||||
if (v == r->f) \
|
||||
return 0; \
|
||||
else if (v) { \
|
||||
ret = copy_##t(v, &tmp); \
|
||||
if (ret) \
|
||||
return ret; \
|
||||
} else \
|
||||
tmp = NULL; \
|
||||
\
|
||||
free_##t(r->f); \
|
||||
r->f = tmp; \
|
||||
\
|
||||
return 0; \
|
||||
}
|
||||
|
||||
#undef _KDC_REQUEST_GET_ACCESSOR_STRUCT
|
||||
#define _KDC_REQUEST_GET_ACCESSOR_STRUCT(R, T, f) \
|
||||
const T * \
|
||||
kdc_request_get_ ## f(R r) \
|
||||
{ \
|
||||
return &r->f; \
|
||||
}
|
||||
|
||||
#undef _KDC_REQUEST_SET_ACCESSOR_STRUCT
|
||||
#define _KDC_REQUEST_SET_ACCESSOR_STRUCT(R, T, t, f) \
|
||||
krb5_error_code \
|
||||
kdc_request_set_ ## f(R r, const T *v) \
|
||||
{ \
|
||||
krb5_error_code ret; \
|
||||
T tmp; \
|
||||
\
|
||||
if (v == NULL) \
|
||||
return EINVAL; \
|
||||
else if (v == &r->f) \
|
||||
return 0; \
|
||||
\
|
||||
ret = copy_##t(v, &tmp); \
|
||||
if (ret) \
|
||||
return ret; \
|
||||
\
|
||||
free_##t(&r->f); \
|
||||
r->f = tmp; \
|
||||
\
|
||||
return 0; \
|
||||
}
|
||||
|
||||
static krb5_error_code
|
||||
copy_string_ptr(const char *src, char **dst)
|
||||
{
|
||||
*dst = strdup(src);
|
||||
if (*dst == NULL)
|
||||
return ENOMEM;
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static void
|
||||
free_string_ptr(char *s)
|
||||
{
|
||||
free(s);
|
||||
}
|
||||
|
||||
static krb5_error_code
|
||||
copy_Principal_ptr(krb5_const_principal src, krb5_principal *dst)
|
||||
{
|
||||
krb5_error_code ret;
|
||||
krb5_principal p;
|
||||
|
||||
*dst = NULL;
|
||||
|
||||
p = calloc(1, sizeof(*p));
|
||||
if (*dst == NULL)
|
||||
return ENOMEM;
|
||||
|
||||
ret = copy_Principal(src, p);
|
||||
if (ret == 0)
|
||||
*dst = p;
|
||||
else
|
||||
free(p);
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
static void
|
||||
free_Principal_ptr(krb5_principal p)
|
||||
{
|
||||
if (p) {
|
||||
free_Principal(p);
|
||||
free(p);
|
||||
}
|
||||
}
|
||||
|
||||
static krb5_error_code
|
||||
copy_pac(const struct krb5_pac_data *src, struct krb5_pac_data **dst)
|
||||
{
|
||||
/* FIXME use heim_copy() when it exists */
|
||||
*dst = (krb5_pac)heim_retain((heim_object_t)src);
|
||||
return 0;
|
||||
}
|
||||
|
||||
static void
|
||||
free_pac(struct krb5_pac_data *o)
|
||||
{
|
||||
heim_release(o);
|
||||
}
|
||||
|
||||
static krb5_error_code
|
||||
copy_keyblock(const EncryptionKey *src, EncryptionKey *dst)
|
||||
{
|
||||
return copy_EncryptionKey(src, dst);
|
||||
}
|
||||
|
||||
static void
|
||||
free_keyblock(EncryptionKey *key)
|
||||
{
|
||||
krb5_free_keyblock_contents(NULL, key);
|
||||
}
|
||||
|
||||
#undef HEIMDAL_KDC_KDC_ACCESSORS_H
|
||||
#include "kdc-accessors.h"
|
||||
|
152
kdc/kdc.h
152
kdc/kdc.h
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (c) 1997-2003 Kungliga Tekniska Högskolan
|
||||
* Copyright (c) 1997-2022 Kungliga Tekniska Högskolan
|
||||
* (Royal Institute of Technology, Stockholm, Sweden).
|
||||
*
|
||||
* Copyright (c) 2005 Andrew Bartlett <abartlet@samba.org>
|
||||
@@ -46,129 +46,27 @@
|
||||
#include <kx509_asn1.h>
|
||||
#include <gssapi/gssapi.h>
|
||||
|
||||
#define heim_pcontext krb5_context
|
||||
#define heim_pconfig krb5_kdc_configuration *
|
||||
#include <heimbase-svc.h>
|
||||
|
||||
enum krb5_kdc_trpolicy {
|
||||
TRPOLICY_ALWAYS_CHECK,
|
||||
TRPOLICY_ALLOW_PER_PRINCIPAL,
|
||||
TRPOLICY_ALWAYS_HONOUR_REQUEST
|
||||
};
|
||||
|
||||
typedef struct krb5_kdc_configuration {
|
||||
krb5_boolean require_preauth; /* require preauth for all principals */
|
||||
time_t kdc_warn_pwexpire; /* time before expiration to print a warning */
|
||||
struct krb5_kdc_configuration;
|
||||
typedef struct krb5_kdc_configuration krb5_kdc_configuration;
|
||||
|
||||
struct HDB **db;
|
||||
int num_db;
|
||||
|
||||
int num_kdc_processes;
|
||||
|
||||
krb5_boolean encode_as_rep_as_tgs_rep; /* bug compatibility */
|
||||
|
||||
/*
|
||||
* Windows 2019 (and earlier versions) always sends the salt
|
||||
* and Samba has testsuites that check this behaviour, so a
|
||||
* Samba AD DC will set this flag to match the AS-REP packet
|
||||
* exactly.
|
||||
*/
|
||||
krb5_boolean force_include_pa_etype_salt;
|
||||
|
||||
krb5_boolean tgt_use_strongest_session_key;
|
||||
krb5_boolean preauth_use_strongest_session_key;
|
||||
krb5_boolean svc_use_strongest_session_key;
|
||||
krb5_boolean use_strongest_server_key;
|
||||
|
||||
krb5_boolean check_ticket_addresses;
|
||||
krb5_boolean warn_ticket_addresses;
|
||||
krb5_boolean allow_null_ticket_addresses;
|
||||
krb5_boolean allow_anonymous;
|
||||
krb5_boolean historical_anon_realm;
|
||||
krb5_boolean strict_nametypes;
|
||||
enum krb5_kdc_trpolicy trpolicy;
|
||||
|
||||
krb5_boolean require_pac;
|
||||
krb5_boolean enable_armored_pa_enc_timestamp;
|
||||
krb5_boolean enable_unarmored_pa_enc_timestamp;
|
||||
|
||||
krb5_boolean enable_pkinit;
|
||||
krb5_boolean pkinit_princ_in_cert;
|
||||
const char *pkinit_kdc_identity;
|
||||
const char *pkinit_kdc_anchors;
|
||||
const char *pkinit_kdc_friendly_name;
|
||||
const char *pkinit_kdc_ocsp_file;
|
||||
char **pkinit_kdc_cert_pool;
|
||||
char **pkinit_kdc_revoke;
|
||||
int pkinit_dh_min_bits;
|
||||
/* XXX Turn these into bit-fields */
|
||||
int pkinit_require_binding;
|
||||
int pkinit_allow_proxy_certs;
|
||||
int synthetic_clients;
|
||||
int pkinit_max_life_from_cert_extension;
|
||||
krb5_timestamp pkinit_max_life_from_cert;
|
||||
krb5_timestamp pkinit_max_life_bound;
|
||||
krb5_timestamp synthetic_clients_max_life;
|
||||
krb5_timestamp synthetic_clients_max_renew;
|
||||
|
||||
krb5_log_facility *logf;
|
||||
|
||||
int enable_digest;
|
||||
int digests_allowed;
|
||||
|
||||
int enable_gss_preauth;
|
||||
int enable_gss_auth_data;
|
||||
gss_OID_set gss_mechanisms_allowed;
|
||||
gss_OID_set gss_cross_realm_mechanisms_allowed;
|
||||
|
||||
size_t max_datagram_reply_length;
|
||||
|
||||
int enable_kx509;
|
||||
|
||||
const char *app;
|
||||
} krb5_kdc_configuration;
|
||||
|
||||
#define ASTGS_REQUEST_DESC_COMMON_ELEMENTS \
|
||||
HEIM_SVC_REQUEST_DESC_COMMON_ELEMENTS; \
|
||||
\
|
||||
/* AS-REQ or TGS-REQ */ \
|
||||
KDC_REQ req; \
|
||||
\
|
||||
/* AS-REP or TGS-REP */ \
|
||||
KDC_REP rep; \
|
||||
EncTicketPart et; \
|
||||
EncKDCRepPart ek; \
|
||||
\
|
||||
/* client principal (AS) or TGT/S4U principal (TGS) */ \
|
||||
krb5_principal client_princ; \
|
||||
hdb_entry *client; \
|
||||
HDB *clientdb; \
|
||||
krb5_principal canon_client_princ; \
|
||||
\
|
||||
/* server principal */ \
|
||||
krb5_principal server_princ; \
|
||||
hdb_entry *server; \
|
||||
HDB *serverdb; \
|
||||
\
|
||||
/* presented ticket in TGS-REQ (unused by AS) */ \
|
||||
krb5_principal *krbtgt_princ; \
|
||||
hdb_entry *krbtgt; \
|
||||
HDB *krbtgtdb; \
|
||||
krb5_ticket *ticket; \
|
||||
\
|
||||
krb5_keyblock reply_key; \
|
||||
\
|
||||
krb5_pac pac; \
|
||||
uint64_t pac_attributes
|
||||
|
||||
#ifndef __KDC_LOCL_H__
|
||||
struct astgs_request_desc {
|
||||
ASTGS_REQUEST_DESC_COMMON_ELEMENTS;
|
||||
};
|
||||
#endif
|
||||
/*
|
||||
* Access to request fields by plugins and other out-of-tree
|
||||
* consumers should be via the functions in kdc-accessors.h.
|
||||
*/
|
||||
|
||||
struct kdc_request_desc;
|
||||
typedef struct kdc_request_desc *kdc_request_t;
|
||||
|
||||
struct astgs_request_desc;
|
||||
typedef struct astgs_request_desc *astgs_request_t;
|
||||
|
||||
struct kx509_req_context_desc;
|
||||
typedef struct kx509_req_context_desc *kx509_req_context;
|
||||
|
||||
struct krb5_kdc_service {
|
||||
@@ -179,9 +77,27 @@ struct krb5_kdc_service {
|
||||
krb5_error_code (*process)(kdc_request_t *, int *claim);
|
||||
};
|
||||
|
||||
/*
|
||||
* The following fields are guaranteed stable within a major
|
||||
* release of Heimdal and can be manipulated by applications
|
||||
* that manage KDC requests themselves using libkdc.
|
||||
*
|
||||
* Applications can make custom KDC configuration available
|
||||
* to libkdc by using krb5_set_config().
|
||||
*/
|
||||
|
||||
#define KRB5_KDC_CONFIGURATION_COMMON_ELEMENTS \
|
||||
krb5_log_facility *logf; \
|
||||
struct HDB **db; \
|
||||
size_t num_db; \
|
||||
const char *app
|
||||
|
||||
#ifndef __KDC_LOCL_H__
|
||||
struct krb5_kdc_configuration {
|
||||
KRB5_KDC_CONFIGURATION_COMMON_ELEMENTS;
|
||||
};
|
||||
#endif
|
||||
|
||||
#include <kdc-protos.h>
|
||||
|
||||
#undef heim_pcontext
|
||||
#undef heim_pconfig
|
||||
|
||||
#endif
|
||||
#endif /* __KDC_H__ */
|
||||
|
@@ -66,8 +66,105 @@ struct kdc_request_desc {
|
||||
|
||||
struct kdc_patypes;
|
||||
|
||||
struct krb5_kdc_configuration {
|
||||
KRB5_KDC_CONFIGURATION_COMMON_ELEMENTS;
|
||||
|
||||
int num_kdc_processes;
|
||||
|
||||
size_t max_datagram_reply_length;
|
||||
|
||||
time_t kdc_warn_pwexpire; /* time before expiration to print a warning */
|
||||
|
||||
unsigned int require_preauth : 1; /* require preauth for all principals */
|
||||
unsigned int encode_as_rep_as_tgs_rep : 1; /* bug compatibility */
|
||||
|
||||
/*
|
||||
* Windows 2019 (and earlier versions) always sends the salt
|
||||
* and Samba has testsuites that check this behaviour, so a
|
||||
* Samba AD DC will set this flag to match the AS-REP packet
|
||||
* exactly.
|
||||
*/
|
||||
unsigned int force_include_pa_etype_salt : 1;
|
||||
|
||||
unsigned int tgt_use_strongest_session_key : 1;
|
||||
unsigned int preauth_use_strongest_session_key : 1;
|
||||
unsigned int svc_use_strongest_session_key : 1;
|
||||
unsigned int use_strongest_server_key : 1;
|
||||
|
||||
unsigned int check_ticket_addresses : 1;
|
||||
unsigned int warn_ticket_addresses : 1;
|
||||
unsigned int allow_null_ticket_addresses : 1;
|
||||
unsigned int allow_anonymous : 1;
|
||||
unsigned int historical_anon_realm : 1;
|
||||
unsigned int strict_nametypes : 1;
|
||||
enum krb5_kdc_trpolicy trpolicy;
|
||||
|
||||
unsigned int require_pac : 1;
|
||||
unsigned int enable_armored_pa_enc_timestamp : 1;
|
||||
unsigned int enable_unarmored_pa_enc_timestamp : 1;
|
||||
|
||||
unsigned int enable_pkinit : 1;
|
||||
unsigned int pkinit_princ_in_cert : 1;
|
||||
const char *pkinit_kdc_identity;
|
||||
const char *pkinit_kdc_anchors;
|
||||
const char *pkinit_kdc_friendly_name;
|
||||
const char *pkinit_kdc_ocsp_file;
|
||||
char **pkinit_kdc_cert_pool;
|
||||
char **pkinit_kdc_revoke;
|
||||
int pkinit_dh_min_bits;
|
||||
unsigned int pkinit_require_binding : 1;
|
||||
unsigned int pkinit_allow_proxy_certs : 1;
|
||||
unsigned int synthetic_clients : 1;
|
||||
unsigned int pkinit_max_life_from_cert_extension : 1;
|
||||
krb5_timestamp pkinit_max_life_from_cert;
|
||||
krb5_timestamp pkinit_max_life_bound;
|
||||
krb5_timestamp synthetic_clients_max_life;
|
||||
krb5_timestamp synthetic_clients_max_renew;
|
||||
|
||||
int digests_allowed;
|
||||
unsigned int enable_digest : 1;
|
||||
|
||||
unsigned int enable_kx509 : 1;
|
||||
|
||||
unsigned int enable_gss_preauth : 1;
|
||||
unsigned int enable_gss_auth_data : 1;
|
||||
gss_OID_set gss_mechanisms_allowed;
|
||||
gss_OID_set gss_cross_realm_mechanisms_allowed;
|
||||
|
||||
};
|
||||
|
||||
struct astgs_request_desc {
|
||||
ASTGS_REQUEST_DESC_COMMON_ELEMENTS;
|
||||
HEIM_SVC_REQUEST_DESC_COMMON_ELEMENTS;
|
||||
|
||||
/* AS-REQ or TGS-REQ */
|
||||
KDC_REQ req;
|
||||
|
||||
/* AS-REP or TGS-REP */
|
||||
KDC_REP rep;
|
||||
EncTicketPart et;
|
||||
EncKDCRepPart ek;
|
||||
|
||||
/* client principal (AS) or TGT/S4U principal (TGS) */
|
||||
krb5_principal client_princ;
|
||||
hdb_entry *client;
|
||||
HDB *clientdb;
|
||||
krb5_principal canon_client_princ;
|
||||
|
||||
/* server principal */
|
||||
krb5_principal server_princ;
|
||||
HDB *serverdb;
|
||||
hdb_entry *server;
|
||||
|
||||
/* presented ticket in TGS-REQ (unused by AS) */
|
||||
krb5_principal krbtgt_princ;
|
||||
hdb_entry *krbtgt;
|
||||
HDB *krbtgtdb;
|
||||
krb5_ticket *ticket;
|
||||
|
||||
krb5_keyblock reply_key;
|
||||
|
||||
krb5_pac pac;
|
||||
uint64_t pac_attributes;
|
||||
|
||||
/* Only AS */
|
||||
const struct kdc_patypes *pa_used;
|
||||
|
@@ -21,6 +21,45 @@ EXPORTS
|
||||
kdc_request_get_attribute
|
||||
kdc_request_copy_attribute
|
||||
kdc_request_delete_attribute
|
||||
kdc_request_add_pac_buffer
|
||||
kdc_request_add_reply_padata
|
||||
kdc_request_get_addr
|
||||
kdc_request_get_canon_client_princ
|
||||
kdc_request_get_client
|
||||
kdc_request_get_clientdb
|
||||
kdc_request_get_client_princ
|
||||
kdc_request_get_context
|
||||
kdc_request_get_config
|
||||
kdc_request_get_cname
|
||||
kdc_request_get_error_code
|
||||
kdc_request_get_from
|
||||
kdc_request_get_krbtgt
|
||||
kdc_request_get_krbtgtdb
|
||||
kdc_request_get_krbtgt_princ
|
||||
kdc_request_get_pac
|
||||
kdc_request_get_pac_attributes
|
||||
kdc_request_get_rep
|
||||
kdc_request_get_reply_key
|
||||
kdc_request_get_req
|
||||
kdc_request_get_request
|
||||
kdc_request_get_server
|
||||
kdc_request_get_serverdb
|
||||
kdc_request_get_server_princ
|
||||
kdc_request_get_sname
|
||||
kdc_request_get_ticket
|
||||
kdc_request_get_tv_end
|
||||
kdc_request_get_tv_start
|
||||
kdc_request_set_canon_client_princ
|
||||
kdc_request_set_client_princ
|
||||
kdc_request_set_cname
|
||||
kdc_request_set_error_code
|
||||
kdc_request_set_krbtgt_princ
|
||||
kdc_request_set_pac
|
||||
kdc_request_set_pac_attributes
|
||||
kdc_request_set_rep
|
||||
kdc_request_set_reply_key
|
||||
kdc_request_set_server_princ
|
||||
kdc_request_set_sname
|
||||
kdc_audit_addkv
|
||||
kdc_audit_addkv_number
|
||||
kdc_audit_addkv_object
|
||||
|
@@ -24,6 +24,45 @@ HEIMDAL_KDC_1.0 {
|
||||
kdc_request_get_attribute;
|
||||
kdc_request_copy_attribute;
|
||||
kdc_request_delete_attribute;
|
||||
kdc_request_add_pac_buffer;
|
||||
kdc_request_add_reply_padata;
|
||||
kdc_request_get_addr;
|
||||
kdc_request_get_canon_client_princ;
|
||||
kdc_request_get_client;
|
||||
kdc_request_get_clientdb;
|
||||
kdc_request_get_client_princ;
|
||||
kdc_request_get_context;
|
||||
kdc_request_get_config;
|
||||
kdc_request_get_cname;
|
||||
kdc_request_get_error_code;
|
||||
kdc_request_get_from;
|
||||
kdc_request_get_krbtgt;
|
||||
kdc_request_get_krbtgtdb;
|
||||
kdc_request_get_krbtgt_princ;
|
||||
kdc_request_get_pac;
|
||||
kdc_request_get_pac_attributes;
|
||||
kdc_request_get_rep;
|
||||
kdc_request_get_reply_key;
|
||||
kdc_request_get_req;
|
||||
kdc_request_get_request;
|
||||
kdc_request_get_server;
|
||||
kdc_request_get_serverdb;
|
||||
kdc_request_get_server_princ;
|
||||
kdc_request_get_sname;
|
||||
kdc_request_get_ticket;
|
||||
kdc_request_get_tv_end;
|
||||
kdc_request_get_tv_start;
|
||||
kdc_request_set_canon_client_princ;
|
||||
kdc_request_set_client_princ;
|
||||
kdc_request_set_cname;
|
||||
kdc_request_set_error_code;
|
||||
kdc_request_set_krbtgt_princ;
|
||||
kdc_request_set_pac;
|
||||
kdc_request_set_pac_attributes;
|
||||
kdc_request_set_rep;
|
||||
kdc_request_set_reply_key;
|
||||
kdc_request_set_server_princ;
|
||||
kdc_request_set_sname;
|
||||
kdc_audit_addkv;
|
||||
kdc_audit_addkv_number;
|
||||
kdc_audit_addkv_object;
|
||||
|
@@ -95,6 +95,7 @@ typedef struct krb5_ntlm_data *krb5_ntlm;
|
||||
|
||||
struct krb5_pac_data;
|
||||
typedef struct krb5_pac_data *krb5_pac;
|
||||
typedef const struct krb5_pac_data *krb5_const_pac;
|
||||
|
||||
typedef struct krb5_rd_req_in_ctx_data *krb5_rd_req_in_ctx;
|
||||
typedef struct krb5_rd_req_out_ctx_data *krb5_rd_req_out_ctx;
|
||||
|
@@ -100,10 +100,14 @@ pac_verify(void *ctx,
|
||||
|
||||
static void logit(const char *what, astgs_request_t r)
|
||||
{
|
||||
krb5_warnx(r->context, "%s: client %s server %s",
|
||||
krb5_context context = kdc_request_get_context((kdc_request_t)r);
|
||||
const char *cname = kdc_request_get_cname((kdc_request_t)r);
|
||||
const char *sname = kdc_request_get_sname((kdc_request_t)r);
|
||||
|
||||
krb5_warnx(context, "%s: client %s server %s",
|
||||
what,
|
||||
r->cname ? r->cname : "<unknown>",
|
||||
r->sname ? r->sname : "<unknown>");
|
||||
cname ? cname : "<unknown>",
|
||||
sname ? sname : "<unknown>");
|
||||
}
|
||||
|
||||
static krb5_error_code KRB5_CALLCONV
|
||||
@@ -136,11 +140,12 @@ finalize_reply(void *ctx, astgs_request_t r)
|
||||
static krb5_error_code KRB5_CALLCONV
|
||||
audit(void *ctx, astgs_request_t r)
|
||||
{
|
||||
krb5_error_code ret = kdc_request_get_error_code((kdc_request_t)r);
|
||||
heim_number_t n;
|
||||
|
||||
logit("audit", r);
|
||||
|
||||
if (r->ret)
|
||||
if (ret)
|
||||
return 0; /* finalize_reply only called in success */
|
||||
|
||||
n = kdc_request_get_attribute((kdc_request_t)r,
|
||||
|
Reference in New Issue
Block a user