ldap_principal2.c revision 2dd2efa5a06a9befe46075cf41e16f57533c9f98
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf#pragma ident "%Z%%M% %I% %E% SMI"
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf/*
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * lib/kdb/kdb_ldap/ldap_principal2.c
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf *
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * Copyright (c) 2004-2005, Novell, Inc.
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * All rights reserved.
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf *
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * Redistribution and use in source and binary forms, with or without
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * modification, are permitted provided that the following conditions are met:
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf *
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * * Redistributions of source code must retain the above copyright notice,
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * this list of conditions and the following disclaimer.
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * * Redistributions in binary form must reproduce the above copyright
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * notice, this list of conditions and the following disclaimer in the
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * documentation and/or other materials provided with the distribution.
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * * The copyright holder's name is not used to endorse or promote products
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * derived from this software without specific prior written permission.
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf *
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * POSSIBILITY OF SUCH DAMAGE.
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf */
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf/*
2dd2efa5a06a9befe46075cf41e16f57533c9f98willf * Copyright 2008 Sun Microsystems, Inc. All rights reserved.
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * Use is subject to license terms.
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf */
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf#include <time.h>
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf#include "ldap_main.h"
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf#include "kdb_ldap.h"
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf#include "ldap_principal.h"
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf#include "princ_xdr.h"
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf#include "ldap_tkt_policy.h"
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf#include "ldap_pwd_policy.h"
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf#include "ldap_err.h"
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf#include <kadm5/admin.h>
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf#include <libintl.h>
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillfextern char* principal_attributes[];
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillfextern char* max_pwd_life_attr[];
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillfstatic char *
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillfgetstringtime(krb5_timestamp);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillfkrb5_error_code
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillfberval2tl_data(struct berval *in, krb5_tl_data **out)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf{
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf *out = (krb5_tl_data *) malloc (sizeof (krb5_tl_data));
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (*out == NULL)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf return ENOMEM;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf (*out)->tl_data_length = in->bv_len - 2;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf (*out)->tl_data_contents = (krb5_octet *) malloc
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf ((*out)->tl_data_length * sizeof (krb5_octet));
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if ((*out)->tl_data_contents == NULL) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf free (*out);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf return ENOMEM;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf /* Solaris Kerberos: need cast */
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf UNSTORE16_INT ((unsigned char *)in->bv_val, (*out)->tl_data_type);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf memcpy ((*out)->tl_data_contents, in->bv_val + 2, (*out)->tl_data_length);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf return 0;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf}
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf/*
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * look up a principal in the directory.
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf */
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillfkrb5_error_code
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillfkrb5_ldap_get_principal(context, searchfor, entries, nentries, more)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf krb5_context context;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf krb5_const_principal searchfor;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf krb5_db_entry *entries; /* filled in */
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf int *nentries; /* how much room/how many found */
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf krb5_boolean *more; /* are there more? */
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf{
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf char *user=NULL, *filter=NULL, **subtree=NULL;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf unsigned int tree=0, ntrees=1, princlen=0;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf krb5_error_code tempst=0, st=0;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf char **values=NULL;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf LDAP *ld=NULL;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf LDAPMessage *result=NULL, *ent=NULL;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf krb5_ldap_context *ldap_context=NULL;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf kdb5_dal_handle *dal_handle=NULL;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf krb5_ldap_server_handle *ldap_server_handle=NULL;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf /* Clear the global error string */
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf krb5_clear_error_message(context);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf /* set initial values */
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf *nentries = 0;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf *more = 0;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf memset(entries, 0, sizeof(*entries));
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (searchfor == NULL)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf return EINVAL;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf dal_handle = (kdb5_dal_handle *) context->db_context;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf ldap_context = (krb5_ldap_context *) dal_handle->db_context;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf CHECK_LDAP_HANDLE(ldap_context);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (is_principal_in_realm(ldap_context, searchfor) != 0) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf *more = 0;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf krb5_set_error_message (context, st, gettext("Principal does not belong to realm"));
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf goto cleanup;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if ((st=krb5_unparse_name(context, searchfor, &user)) != 0)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf goto cleanup;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if ((st=krb5_ldap_unparse_principal_name(user)) != 0)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf goto cleanup;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf princlen = strlen(FILTER) + strlen(user) + 2 + 1; /* 2 for closing brackets */
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if ((filter = malloc(princlen)) == NULL) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf st = ENOMEM;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf goto cleanup;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf snprintf(filter, princlen, FILTER"%s))", user);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if ((st = krb5_get_subtree_info(ldap_context, &subtree, &ntrees)) != 0)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf goto cleanup;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf GET_HANDLE();
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf for (tree=0; tree < ntrees && *nentries == 0; ++tree) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf LDAP_SEARCH(subtree[tree], ldap_context->lrparams->search_scope, filter, principal_attributes);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf for (ent=ldap_first_entry(ld, result); ent != NULL && *nentries == 0; ent=ldap_next_entry(ld, ent)) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf /* get the associated directory user information */
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if ((values=ldap_get_values(ld, ent, "krbprincipalname")) != NULL) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf int i;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf /* a wild-card in a principal name can return a list of kerberos principals.
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * Make sure that the correct principal is returned.
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * NOTE: a principalname k* in ldap server will return all the principals starting with a k
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf */
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf for (i=0; values[i] != NULL; ++i) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (strcasecmp(values[i], user) == 0) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf *nentries = 1;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf break;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf ldap_value_free(values);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (*nentries == 0) /* no matching principal found */
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf continue;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if ((st = populate_krb5_db_entry(context, ldap_context, ld, ent, searchfor,
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf entries)) != 0)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf goto cleanup;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf ldap_msgfree(result);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf result = NULL;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf } /* for (tree=0 ... */
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf /* once done, put back the ldap handle */
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf krb5_ldap_put_handle_to_pool(ldap_context, ldap_server_handle);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf ldap_server_handle = NULL;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillfcleanup:
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf ldap_msgfree(result);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (*nentries == 0 || st != 0)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf krb5_dbe_free_contents(context, entries);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (filter)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf free (filter);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (subtree) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf for (; ntrees; --ntrees)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (subtree[ntrees-1])
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf free (subtree[ntrees-1]);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf free (subtree);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (ldap_server_handle)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf krb5_ldap_put_handle_to_pool(ldap_context, ldap_server_handle);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (user)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf free(user);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf return st;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf}
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillftypedef enum{ ADD_PRINCIPAL, MODIFY_PRINCIPAL } OPERATION;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf/*
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * ptype is creating confusions. Additionally the logic
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * surronding ptype is redundunt and can be achevied
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * with the help of dn and containerdn members.
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * so dropping the ptype member
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf */
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillftypedef struct _xargs_t {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf char *dn;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf char *linkdn;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf krb5_boolean dn_from_kbd;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf char *containerdn;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf char *tktpolicydn;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf}xargs_t;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillfstatic void
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillffree_xargs(xargs)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf xargs_t xargs;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf{
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (xargs.dn)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf free (xargs.dn);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (xargs.linkdn)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf free(xargs.linkdn);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (xargs.containerdn)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf free (xargs.containerdn);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (xargs.tktpolicydn)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf free (xargs.tktpolicydn);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf}
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillfstatic krb5_error_code
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillfprocess_db_args(context, db_args, xargs, optype)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf krb5_context context;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf char **db_args;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf xargs_t *xargs;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf OPERATION optype;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf{
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf int i=0;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf krb5_error_code st=0;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf char errbuf[1024];
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf char *arg=NULL, *arg_val=NULL;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf char **dptr=NULL;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf unsigned int arg_val_len=0;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (db_args) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf for (i=0; db_args[i]; ++i) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf arg = strtok_r(db_args[i], "=", &arg_val);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (strcmp(arg, TKTPOLICY_ARG) == 0) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf dptr = &xargs->tktpolicydn;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf } else {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (strcmp(arg, USERDN_ARG) == 0) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (optype == MODIFY_PRINCIPAL ||
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf xargs->dn != NULL || xargs->containerdn != NULL ||
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf xargs->linkdn != NULL) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf st = EINVAL;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf snprintf(errbuf, sizeof(errbuf),
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf gettext("%s option not supported"), arg);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf krb5_set_error_message(context, st, "%s", errbuf);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf goto cleanup;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf dptr = &xargs->dn;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf } else if (strcmp(arg, CONTAINERDN_ARG) == 0) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (optype == MODIFY_PRINCIPAL ||
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf xargs->dn != NULL || xargs->containerdn != NULL) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf st = EINVAL;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf snprintf(errbuf, sizeof(errbuf),
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf gettext("%s option not supported"), arg);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf krb5_set_error_message(context, st, "%s", errbuf);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf goto cleanup;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf dptr = &xargs->containerdn;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf } else if (strcmp(arg, LINKDN_ARG) == 0) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (xargs->dn != NULL || xargs->linkdn != NULL) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf st = EINVAL;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf snprintf(errbuf, sizeof(errbuf),
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf gettext("%s option not supported"), arg);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf krb5_set_error_message(context, st, "%s", errbuf);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf goto cleanup;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf dptr = &xargs->linkdn;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf } else {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf st = EINVAL;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf snprintf(errbuf, sizeof(errbuf), gettext("unknown option: %s"), arg);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf krb5_set_error_message(context, st, "%s", errbuf);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf goto cleanup;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf xargs->dn_from_kbd = TRUE;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (arg_val == NULL || strlen(arg_val) == 0) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf st = EINVAL;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf snprintf(errbuf, sizeof(errbuf),
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf gettext("%s option value missing"), arg);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf krb5_set_error_message(context, st, "%s", errbuf);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf goto cleanup;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (arg_val == NULL) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf st = EINVAL;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf snprintf(errbuf, sizeof(errbuf),
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf gettext("%s option value missing"), arg);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf krb5_set_error_message(context, st, "%s", errbuf);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf goto cleanup;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf arg_val_len = strlen(arg_val) + 1;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (strcmp(arg, TKTPOLICY_ARG) == 0) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if ((st = krb5_ldap_name_to_policydn (context,
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf arg_val,
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf dptr)) != 0)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf goto cleanup;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf } else {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf *dptr = calloc (1, arg_val_len);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (*dptr == NULL) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf st = ENOMEM;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf goto cleanup;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf memcpy(*dptr, arg_val, arg_val_len);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillfcleanup:
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf return st;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf}
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillfkrb5int_access accessor;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillfextern int kldap_ensure_initialized (void);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillfstatic krb5_error_code
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillfasn1_encode_sequence_of_keys (krb5_key_data *key_data, krb5_int16 n_key_data,
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf krb5_int32 mkvno, krb5_data **code)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf{
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf krb5_error_code err;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf /*
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * This should be pushed back into other library initialization
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * code.
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf */
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf err = kldap_ensure_initialized ();
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (err)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf return err;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf return accessor.asn1_ldap_encode_sequence_of_keys(key_data, n_key_data,
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf mkvno, code);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf}
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillfstatic krb5_error_code
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillfasn1_decode_sequence_of_keys (krb5_data *in, krb5_key_data **out,
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf krb5_int16 *n_key_data, int *mkvno)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf{
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf krb5_error_code err;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf /*
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * This should be pushed back into other library initialization
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * code.
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf */
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf err = kldap_ensure_initialized ();
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (err)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf return err;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf return accessor.asn1_ldap_decode_sequence_of_keys(in, out, n_key_data,
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf mkvno);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf}
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf/* Decoding ASN.1 encoded key */
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillfstatic struct berval **
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillfkrb5_encode_krbsecretkey(krb5_key_data *key_data, int n_key_data) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf struct berval **ret = NULL;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf int currkvno;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf int num_versions = 1;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf int i, j, last;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf krb5_error_code err = 0;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (n_key_data <= 0)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf return NULL;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf /* Find the number of key versions */
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf for (i = 0; i < n_key_data - 1; i++)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (key_data[i].key_data_kvno != key_data[i + 1].key_data_kvno)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf num_versions++;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf ret = (struct berval **) calloc (num_versions + 1, sizeof (struct berval *));
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (ret == NULL) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf err = ENOMEM;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf goto cleanup;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf for (i = 0, last = 0, j = 0, currkvno = key_data[0].key_data_kvno; i < n_key_data; i++) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf krb5_data *code;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (i == n_key_data - 1 || key_data[i + 1].key_data_kvno != currkvno) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf code = NULL;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf asn1_encode_sequence_of_keys (key_data+last,
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf (krb5_int16) i - last + 1,
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf 0, /* For now, mkvno == 0*/
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf &code);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (code == NULL) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf err = ENOMEM;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf goto cleanup;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf ret[j] = malloc (sizeof (struct berval));
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (ret[j] == NULL) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf err = ENOMEM;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf goto cleanup;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf /*CHECK_NULL(ret[j]); */
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf ret[j]->bv_len = code->length;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf ret[j]->bv_val = code->data;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf j++;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf last = i + 1;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf currkvno = key_data[i].key_data_kvno;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf /* Solaris Kerberos: fix memleak */
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf free(code);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf ret[num_versions] = NULL;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillfcleanup:
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (err != 0) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (ret != NULL) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf for (i = 0; i <= num_versions; i++)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (ret[i] != NULL)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf free (ret[i]);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf free (ret);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf ret = NULL;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf return ret;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf}
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillfstatic krb5_error_code tl_data2berval (krb5_tl_data *in, struct berval **out) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf *out = (struct berval *) malloc (sizeof (struct berval));
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (*out == NULL)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf return ENOMEM;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf (*out)->bv_len = in->tl_data_length + 2;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf (*out)->bv_val = (char *) malloc ((*out)->bv_len);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if ((*out)->bv_val == NULL) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf free (*out);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf return ENOMEM;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf /* Solaris Kerberos: need cast */
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf STORE16_INT((unsigned char *)(*out)->bv_val, in->tl_data_type);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf memcpy ((*out)->bv_val + 2, in->tl_data_contents, in->tl_data_length);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf return 0;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf}
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillfkrb5_error_code
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillfkrb5_ldap_put_principal(context, entries, nentries, db_args)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf krb5_context context;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf krb5_db_entry *entries;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf register int *nentries; /* number of entry structs to update */
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf char **db_args;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf{
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf int i=0, l=0, kerberos_principal_object_type=0;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf krb5_error_code st=0, tempst=0;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf LDAP *ld=NULL;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf LDAPMessage *result=NULL, *ent=NULL;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf char *user=NULL, *subtree=NULL, *principal_dn=NULL;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf char **values=NULL, *strval[10]={NULL}, errbuf[1024];
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf struct berval **bersecretkey=NULL;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf LDAPMod **mods=NULL;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf krb5_boolean create_standalone_prinicipal=FALSE;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf krb5_boolean krb_identity_exists=FALSE, establish_links=FALSE;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf char *standalone_principal_dn=NULL;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf krb5_tl_data *tl_data=NULL;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf kdb5_dal_handle *dal_handle=NULL;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf krb5_ldap_context *ldap_context=NULL;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf krb5_ldap_server_handle *ldap_server_handle=NULL;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf osa_princ_ent_rec princ_ent;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf xargs_t xargs = {0};
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf char *polname = NULL;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf OPERATION optype;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf krb5_boolean found_entry = FALSE;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf struct berval **ber_tl_data = NULL;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf /* Clear the global error string */
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf krb5_clear_error_message(context);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf SETUP_CONTEXT();
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (ldap_context->lrparams == NULL || ldap_context->krbcontainer == NULL)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf return EINVAL;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf /* get ldap handle */
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf GET_HANDLE();
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf for (i=0; i < *nentries; ++i, ++entries) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (is_principal_in_realm(ldap_context, entries->princ) != 0) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf st = EINVAL;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf krb5_set_error_message(context, st, gettext("Principal does not belong to the default realm"));
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf goto cleanup;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf /* get the principal information to act on */
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (entries->princ) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (((st=krb5_unparse_name(context, entries->princ, &user)) != 0) ||
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf ((st=krb5_ldap_unparse_principal_name(user)) != 0))
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf goto cleanup;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf /* Identity the type of operation, it can be
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * add principal or modify principal.
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * hack if the entries->mask has KRB_PRINCIPAL flag set
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * then it is a add operation
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf */
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (entries->mask & KADM5_PRINCIPAL)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf optype = ADD_PRINCIPAL;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf else
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf optype = MODIFY_PRINCIPAL;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (((st=krb5_get_princ_type(context, entries, &kerberos_principal_object_type)) != 0) ||
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf ((st=krb5_get_userdn(context, entries, &principal_dn)) != 0))
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf goto cleanup;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if ((st=process_db_args(context, db_args, &xargs, optype)) != 0)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf goto cleanup;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (entries->mask & KADM5_LOAD) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf int tree = 0, princlen = 0, numlentries = 0;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf unsigned int ntrees = 0;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf char **subtreelist = NULL, *filter = NULL;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf /* A load operation is special, will do a mix-in (add krbprinc
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * attrs to a non-krb object entry) if an object exists with a
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * matching krbprincipalname attribute so try to find existing
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * object and set principal_dn. This assumes that the
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * krbprincipalname attribute is unique (only one object entry has
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * a particular krbprincipalname attribute).
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf */
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (user == NULL) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf /* must have principal name for search */
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf st = EINVAL;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf krb5_set_error_message(context, st, gettext("operation can not continue, principal name not found"));
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf goto cleanup;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf princlen = strlen(FILTER) + strlen(user) + 2 + 1; /* 2 for closing brackets */
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if ((filter = malloc(princlen)) == NULL) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf st = ENOMEM;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf goto cleanup;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf snprintf(filter, princlen, FILTER"%s))", user);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf /* get the current subtree list */
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if ((st = krb5_get_subtree_info(ldap_context, &subtreelist, &ntrees)) != 0)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf goto cleanup;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf found_entry = FALSE;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf /* search for entry with matching krbprincipalname attribute */
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf for (tree = 0; found_entry == FALSE && tree < ntrees; ++tree) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf result = NULL;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (principal_dn == NULL) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf LDAP_SEARCH_1(subtreelist[tree], ldap_context->lrparams->search_scope, filter, principal_attributes, IGNORE_STATUS);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf } else {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf /* just look for entry with principal_dn */
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf LDAP_SEARCH_1(principal_dn, LDAP_SCOPE_BASE, filter, principal_attributes, IGNORE_STATUS);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (st == LDAP_SUCCESS) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf numlentries = ldap_count_entries(ld, result);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (numlentries > 1) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf ldap_msgfree(result);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf free(filter);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf st = EINVAL;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf krb5_set_error_message(context, st,
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf gettext("operation can not continue, more than one entry with principal name \"%s\" found"),
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf user);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf goto cleanup;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf } else if (numlentries == 1) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf found_entry = TRUE;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (principal_dn == NULL) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf ent = ldap_first_entry(ld, result);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (ent != NULL) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf /* setting principal_dn will cause that entry to be modified further down */
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if ((principal_dn = ldap_get_dn(ld, ent)) == NULL) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf ldap_get_option (ld, LDAP_OPT_RESULT_CODE, &st);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf st = set_ldap_error (context, st, 0);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf ldap_msgfree(result);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf free(filter);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf goto cleanup;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (result)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf ldap_msgfree(result);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf } else if (st != LDAP_NO_SUCH_OBJECT) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf /* could not perform search, return with failure */
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf st = set_ldap_error (context, st, 0);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf free(filter);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf goto cleanup;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf /*
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * If it isn't found then assume a standalone princ entry is to
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * be created.
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf */
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf } /* end for (tree = 0; principal_dn == ... */
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf free(filter);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (found_entry == FALSE && principal_dn != NULL) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf /*
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * if principal_dn is null then there is code further down to
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * deal with setting standalone_principal_dn. Also note that
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * this will set create_standalone_prinicipal true for
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * non-mix-in entries which is okay if loading from a dump.
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf */
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf create_standalone_prinicipal = TRUE;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf standalone_principal_dn = strdup(principal_dn);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf CHECK_NULL(standalone_principal_dn);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf } /* end if (entries->mask & KADM5_LOAD */
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf /* time to generate the DN information with the help of
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * containerdn, principalcontainerreference or
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * realmcontainerdn information
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf */
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (principal_dn == NULL && xargs.dn == NULL) { /* creation of standalone principal */
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf /* get the subtree information */
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (entries->princ->length == 2 && entries->princ->data[0].length == strlen("krbtgt") &&
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf strncmp(entries->princ->data[0].data, "krbtgt", entries->princ->data[0].length) == 0) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf /* if the principal is a inter-realm principal, always created in the realm container */
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf subtree = strdup(ldap_context->lrparams->realmdn);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf } else if (xargs.containerdn) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if ((st=checkattributevalue(ld, xargs.containerdn, NULL, NULL, NULL)) != 0) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (st == KRB5_KDB_NOENTRY || st == KRB5_KDB_CONSTRAINT_VIOLATION) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf int ost = st;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf st = EINVAL;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf snprintf(errbuf, sizeof(errbuf), gettext("'%s' not found: "), xargs.containerdn);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf prepend_err_str(context, errbuf, st, ost);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf goto cleanup;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf subtree = strdup(xargs.containerdn);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf } else if (ldap_context->lrparams->containerref && strlen(ldap_context->lrparams->containerref) != 0) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf /*
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * Here the subtree should be changed with
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * principalcontainerreference attribute value
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf */
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf subtree = strdup(ldap_context->lrparams->containerref);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf } else {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf subtree = strdup(ldap_context->lrparams->realmdn);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf CHECK_NULL(subtree);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf standalone_principal_dn = malloc(strlen("krbprincipalname=") + strlen(user) + strlen(",") +
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf strlen(subtree) + 1);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf CHECK_NULL(standalone_principal_dn);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf /*LINTED*/
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf sprintf(standalone_principal_dn, "krbprincipalname=%s,%s", user, subtree);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf /*
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * free subtree when you are done using the subtree
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * set the boolean create_standalone_prinicipal to TRUE
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf */
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf create_standalone_prinicipal = TRUE;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf free(subtree);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf subtree = NULL;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf /*
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * If the DN information is presented by the user, time to
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * validate the input to ensure that the DN falls under
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * any of the subtrees
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf */
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (xargs.dn_from_kbd == TRUE) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf /* make sure the DN falls in the subtree */
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf int tre=0, dnlen=0, subtreelen=0;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf unsigned int ntrees = 0;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf char **subtreelist=NULL;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf char *dn=NULL;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf krb5_boolean outofsubtree=TRUE;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (xargs.dn != NULL) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf dn = xargs.dn;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf } else if (xargs.linkdn != NULL) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf dn = xargs.linkdn;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf } else if (standalone_principal_dn != NULL) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf /*
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * Even though the standalone_principal_dn is constructed
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * within this function, there is the containerdn input
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * from the user that can become part of the it.
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf */
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf dn = standalone_principal_dn;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf /* get the current subtree list */
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if ((st = krb5_get_subtree_info(ldap_context, &subtreelist, &ntrees)) != 0)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf goto cleanup;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf for (tre=0; tre<ntrees; ++tre) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (subtreelist[tre] == NULL || strlen(subtreelist[tre]) == 0) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf outofsubtree = FALSE;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf break;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf } else {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf dnlen = strlen (dn);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf subtreelen = strlen(subtreelist[tre]);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if ((dnlen >= subtreelen) && (strcasecmp((dn + dnlen - subtreelen), subtreelist[tre]) == 0)) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf outofsubtree = FALSE;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf break;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf for (tre=0; tre < ntrees; ++tre) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf free(subtreelist[tre]);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (outofsubtree == TRUE) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf st = EINVAL;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf krb5_set_error_message(context, st, gettext("DN is out of the realm subtree"));
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf goto cleanup;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf /*
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * dn value will be set either by dn, linkdn or the standalone_principal_dn
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * In the first 2 cases, the dn should be existing and in the last case we
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * are supposed to create the ldap object. so the below should not be
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * executed for the last case.
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf */
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (standalone_principal_dn == NULL) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf /*
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * If the ldap object is missing, this results in an error.
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf */
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf /*
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * Search for krbprincipalname attribute here.
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * This is to find if a kerberos identity is already present
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * on the ldap object, in which case adding a kerberos identity
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * on the ldap object should result in an error.
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf */
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf char *attributes[]={"krbticketpolicyreference", "krbprincipalname", NULL};
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf LDAP_SEARCH_1(dn, LDAP_SCOPE_BASE, 0, attributes, IGNORE_STATUS);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (st == LDAP_SUCCESS) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf ent = ldap_first_entry(ld, result);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (ent != NULL) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if ((values=ldap_get_values(ld, ent, "krbticketpolicyreference")) != NULL) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf ldap_value_free(values);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if ((values=ldap_get_values(ld, ent, "krbprincipalname")) != NULL) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf krb_identity_exists = TRUE;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf ldap_value_free(values);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf ldap_msgfree(result);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf } else {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf st = set_ldap_error(context, st, OP_SEARCH);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf goto cleanup;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf /*
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * If xargs.dn is set then the request is to add a
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * kerberos principal on a ldap object, but if
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * there is one already on the ldap object this
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * should result in an error.
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf */
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (xargs.dn != NULL && krb_identity_exists == TRUE) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf st = EINVAL;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf snprintf(errbuf, sizeof(errbuf), gettext("ldap object is already kerberized"));
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf krb5_set_error_message(context, st, "%s", errbuf);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf goto cleanup;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (xargs.linkdn != NULL) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf /*
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * link information can be changed using modprinc.
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * However, link information can be changed only on the
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * standalone kerberos principal objects. A standalone
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * kerberos principal object is of type krbprincipal
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * structural objectclass.
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf *
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * NOTE: kerberos principals on an ldap object can't be
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * linked to other ldap objects.
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf */
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (optype == MODIFY_PRINCIPAL &&
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf kerberos_principal_object_type != KDB_STANDALONE_PRINCIPAL_OBJECT) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf st = EINVAL;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf snprintf(errbuf, sizeof(errbuf),
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf gettext("link information can not be set/updated as the kerberos principal belongs to an ldap object"));
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf krb5_set_error_message(context, st, "%s", errbuf);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf goto cleanup;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf /*
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * Check the link information. If there is already a link
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * existing then this operation is not allowed.
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf */
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf char **linkdns=NULL;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf int j=0;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if ((st=krb5_get_linkdn(context, entries, &linkdns)) != 0) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf snprintf(errbuf, sizeof(errbuf),
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf gettext("Failed getting object references"));
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf krb5_set_error_message(context, st, "%s", errbuf);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf goto cleanup;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (linkdns != NULL) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf st = EINVAL;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf snprintf(errbuf, sizeof(errbuf),
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf gettext("kerberos principal is already linked "
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf "to a ldap object"));
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf krb5_set_error_message(context, st, "%s", errbuf);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf for (j=0; linkdns[j] != NULL; ++j)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf free (linkdns[j]);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf free (linkdns);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf goto cleanup;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf establish_links = TRUE;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if ((entries->last_success)!=0) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf memset(strval, 0, sizeof(strval));
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if ((strval[0]=getstringtime(entries->last_success)) == NULL)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf goto cleanup;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if ((st=krb5_add_str_mem_ldap_mod(&mods, "krbLastSuccessfulAuth", LDAP_MOD_REPLACE, strval)) != 0) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf free (strval[0]);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf goto cleanup;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf free (strval[0]);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (entries->last_failed!=0) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf memset(strval, 0, sizeof(strval));
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if ((strval[0]=getstringtime(entries->last_failed)) == NULL)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf goto cleanup;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if ((st=krb5_add_str_mem_ldap_mod(&mods, "krbLastFailedAuth", LDAP_MOD_REPLACE, strval)) != 0) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf free (strval[0]);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf goto cleanup;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf free(strval[0]);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (entries->fail_auth_count!=0) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if ((st=krb5_add_int_mem_ldap_mod(&mods, "krbLoginFailedCount", LDAP_MOD_REPLACE, entries->fail_auth_count)) !=0)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf goto cleanup;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (entries->mask & KADM5_MAX_LIFE) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if ((st=krb5_add_int_mem_ldap_mod(&mods, "krbmaxticketlife", LDAP_MOD_REPLACE, entries->max_life)) != 0)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf goto cleanup;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (entries->mask & KADM5_MAX_RLIFE) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if ((st=krb5_add_int_mem_ldap_mod(&mods, "krbmaxrenewableage", LDAP_MOD_REPLACE,
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf entries->max_renewable_life)) != 0)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf goto cleanup;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (entries->mask & KADM5_ATTRIBUTES) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if ((st=krb5_add_int_mem_ldap_mod(&mods, "krbticketflags", LDAP_MOD_REPLACE,
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf entries->attributes)) != 0)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf goto cleanup;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (entries->mask & KADM5_PRINCIPAL) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf memset(strval, 0, sizeof(strval));
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf strval[0] = user;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if ((st=krb5_add_str_mem_ldap_mod(&mods, "krbprincipalname", LDAP_MOD_REPLACE, strval)) != 0)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf goto cleanup;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf /*
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * Solaris Kerberos: this logic was not working properly when
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * default_principal_expiration set.
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf */
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (entries->mask & KADM5_PRINC_EXPIRE_TIME || entries->expiration != 0) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf memset(strval, 0, sizeof(strval));
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if ((strval[0]=getstringtime(entries->expiration)) == NULL)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf goto cleanup;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if ((st=krb5_add_str_mem_ldap_mod(&mods, "krbprincipalexpiration", LDAP_MOD_REPLACE, strval)) != 0) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf free (strval[0]);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf goto cleanup;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf free (strval[0]);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf /*
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * Solaris Kerberos: in case KADM5_PW_EXPIRATION isn't set, check
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * pw_expiration
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf */
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (entries->mask & KADM5_PW_EXPIRATION || entries->pw_expiration != 0) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf memset(strval, 0, sizeof(strval));
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if ((strval[0]=getstringtime(entries->pw_expiration)) == NULL)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf goto cleanup;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if ((st=krb5_add_str_mem_ldap_mod(&mods, "krbpasswordexpiration",
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf LDAP_MOD_REPLACE,
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf strval)) != 0) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf free (strval[0]);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf goto cleanup;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf free (strval[0]);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (entries->mask & KADM5_POLICY) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf memset(&princ_ent, 0, sizeof(princ_ent));
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf for (tl_data=entries->tl_data; tl_data; tl_data=tl_data->tl_data_next) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (tl_data->tl_data_type == KRB5_TL_KADM_DATA) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf /* FIX ME: I guess the princ_ent should be freed after this call */
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if ((st = krb5_lookup_tl_kadm_data(tl_data, &princ_ent)) != 0) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf goto cleanup;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (princ_ent.aux_attributes & KADM5_POLICY) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf memset(strval, 0, sizeof(strval));
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if ((st = krb5_ldap_name_to_policydn (context, princ_ent.policy, &polname)) != 0)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf goto cleanup;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf strval[0] = polname;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf /* Solaris Kerberos: fix memleak */
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf free(princ_ent.policy);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if ((st=krb5_add_str_mem_ldap_mod(&mods, "krbpwdpolicyreference", LDAP_MOD_REPLACE, strval)) != 0)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf goto cleanup;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf } else {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf st = EINVAL;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf krb5_set_error_message(context, st, gettext("Password policy value null"));
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf goto cleanup;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf } else if (entries->mask & KADM5_LOAD && found_entry == TRUE) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf /*
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * a load is special in that existing entries must have attrs that
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * removed.
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf */
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if ((st=krb5_add_str_mem_ldap_mod(&mods, "krbpwdpolicyreference", LDAP_MOD_REPLACE, NULL)) != 0)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf goto cleanup;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (entries->mask & KADM5_POLICY_CLR) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if ((st=krb5_add_str_mem_ldap_mod(&mods, "krbpwdpolicyreference", LDAP_MOD_DELETE, NULL)) != 0)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf goto cleanup;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (entries->mask & KADM5_KEY_DATA || entries->mask & KADM5_KVNO) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf bersecretkey = krb5_encode_krbsecretkey (entries->key_data,
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf entries->n_key_data);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if ((st=krb5_add_ber_mem_ldap_mod(&mods, "krbprincipalkey",
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf LDAP_MOD_REPLACE | LDAP_MOD_BVALUES, bersecretkey)) != 0)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf goto cleanup;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (!(entries->mask & KADM5_PRINCIPAL)) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf memset(strval, 0, sizeof(strval));
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if ((strval[0]=getstringtime(entries->pw_expiration)) == NULL)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf goto cleanup;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if ((st=krb5_add_str_mem_ldap_mod(&mods,
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf "krbpasswordexpiration",
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf LDAP_MOD_REPLACE, strval)) != 0) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf free (strval[0]);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf goto cleanup;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf free (strval[0]);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf /* Update last password change whenever a new key is set */
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf krb5_timestamp last_pw_changed;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if ((st=krb5_dbe_lookup_last_pwd_change(context, entries,
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf &last_pw_changed)) != 0)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf goto cleanup;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf memset(strval, 0, sizeof(strval));
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if ((strval[0] = getstringtime(last_pw_changed)) == NULL)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf goto cleanup;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if ((st=krb5_add_str_mem_ldap_mod(&mods, "krbLastPwdChange",
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf LDAP_MOD_REPLACE, strval)) != 0) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf free (strval[0]);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf goto cleanup;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf free (strval[0]);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf } /* Modify Key data ends here */
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf /* Set tl_data */
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (entries->tl_data != NULL) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf int count = 0;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf /* struct berval **ber_tl_data = NULL; */
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf krb5_tl_data *ptr;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf for (ptr = entries->tl_data; ptr != NULL; ptr = ptr->tl_data_next) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (ptr->tl_data_type == KRB5_TL_LAST_PWD_CHANGE
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf#ifdef SECURID
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf || ptr->tl_data_type == KRB5_TL_DB_ARGS
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf#endif
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf || ptr->tl_data_type == KDB_TL_USER_INFO)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf continue;
2dd2efa5a06a9befe46075cf41e16f57533c9f98willf
2dd2efa5a06a9befe46075cf41e16f57533c9f98willf /* Solaris Kerberos: fix key history issue */
2dd2efa5a06a9befe46075cf41e16f57533c9f98willf if (ptr->tl_data_type == KRB5_TL_KADM_DATA && ! entries->mask & KADM5_KEY_HIST)
2dd2efa5a06a9befe46075cf41e16f57533c9f98willf continue;
2dd2efa5a06a9befe46075cf41e16f57533c9f98willf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf count++;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (count != 0) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf int j;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf ber_tl_data = (struct berval **) calloc (count + 1,
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf sizeof (struct berval*));
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (ber_tl_data == NULL) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf st = ENOMEM;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf goto cleanup;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf for (j = 0, ptr = entries->tl_data; ptr != NULL; ptr = ptr->tl_data_next) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf /* Ignore tl_data that are stored in separate directory
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * attributes */
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (ptr->tl_data_type == KRB5_TL_LAST_PWD_CHANGE
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf#ifdef SECURID
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf || ptr->tl_data_type == KRB5_TL_DB_ARGS
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf#endif
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf || ptr->tl_data_type == KDB_TL_USER_INFO)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf continue;
2dd2efa5a06a9befe46075cf41e16f57533c9f98willf
2dd2efa5a06a9befe46075cf41e16f57533c9f98willf /*
2dd2efa5a06a9befe46075cf41e16f57533c9f98willf * Solaris Kerberos: key history needs to be stored (it's in
2dd2efa5a06a9befe46075cf41e16f57533c9f98willf * the KRB5_TL_KADM_DATA).
2dd2efa5a06a9befe46075cf41e16f57533c9f98willf */
2dd2efa5a06a9befe46075cf41e16f57533c9f98willf if (ptr->tl_data_type == KRB5_TL_KADM_DATA && ! entries->mask & KADM5_KEY_HIST)
2dd2efa5a06a9befe46075cf41e16f57533c9f98willf continue;
2dd2efa5a06a9befe46075cf41e16f57533c9f98willf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if ((st = tl_data2berval (ptr, &ber_tl_data[j])) != 0)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf break;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf j++;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (st != 0) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf /* Solaris Kerberos: don't free here, do it at cleanup */
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf goto cleanup;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf ber_tl_data[count] = NULL;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if ((st=krb5_add_ber_mem_ldap_mod(&mods, "krbExtraData",
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf LDAP_MOD_REPLACE | LDAP_MOD_BVALUES,
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf ber_tl_data)) != 0)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf goto cleanup;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf /* Directory specific attribute */
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (xargs.tktpolicydn != NULL) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf int tmask=0;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (strlen(xargs.tktpolicydn) != 0) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf st = checkattributevalue(ld, xargs.tktpolicydn, "objectclass", policyclass, &tmask);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf CHECK_CLASS_VALIDITY(st, tmask, "ticket policy object value: ");
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf strval[0] = xargs.tktpolicydn;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf strval[1] = NULL;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if ((st=krb5_add_str_mem_ldap_mod(&mods, "krbticketpolicyreference", LDAP_MOD_REPLACE, strval)) != 0)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf goto cleanup;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf } else {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf /* if xargs.tktpolicydn is a empty string, then delete
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * already existing krbticketpolicyreference attr */
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if ((st=krb5_add_str_mem_ldap_mod(&mods, "krbticketpolicyreference", LDAP_MOD_DELETE, NULL)) != 0)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf goto cleanup;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (establish_links == TRUE) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf memset(strval, 0, sizeof(strval));
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf strval[0] = xargs.linkdn;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if ((st=krb5_add_str_mem_ldap_mod(&mods, "krbObjectReferences", LDAP_MOD_REPLACE, strval)) != 0)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf goto cleanup;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf /*
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * in case mods is NULL then return
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * not sure but can happen in a modprinc
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * so no need to return an error
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * addprinc will at least have the principal name
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * and the keys passed in
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf */
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (mods == NULL)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf goto cleanup;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (create_standalone_prinicipal == TRUE) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf memset(strval, 0, sizeof(strval));
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf strval[0] = "krbprincipal";
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf strval[1] = "krbprincipalaux";
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf strval[2] = "krbTicketPolicyAux";
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if ((st=krb5_add_str_mem_ldap_mod(&mods, "objectclass", LDAP_MOD_ADD, strval)) != 0)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf goto cleanup;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf st = ldap_add_ext_s(ld, standalone_principal_dn, mods, NULL, NULL);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (st == LDAP_ALREADY_EXISTS && entries->mask & KADM5_LOAD) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf /* a load operation must replace an existing entry */
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf st = ldap_delete_ext_s(ld, standalone_principal_dn, NULL, NULL);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (st != LDAP_SUCCESS) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf snprintf(errbuf, sizeof (errbuf), gettext("Principal delete failed (trying to replace entry): %s"),
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf ldap_err2string(st));
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf st = translate_ldap_error (st, OP_ADD);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf krb5_set_error_message(context, st, "%s", errbuf);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf goto cleanup;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf } else {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf st = ldap_add_ext_s(ld, standalone_principal_dn, mods, NULL, NULL);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (st != LDAP_SUCCESS) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf snprintf(errbuf, sizeof (errbuf), gettext("Principal add failed: %s"), ldap_err2string(st));
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf st = translate_ldap_error (st, OP_ADD);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf krb5_set_error_message(context, st, "%s", errbuf);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf goto cleanup;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf } else {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf /*
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * Here existing ldap object is modified and can be related
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * to any attribute, so always ensure that the ldap
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * object is extended with all the kerberos related
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * objectclasses so that there are no constraint
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf * violations.
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf */
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf char *attrvalues[] = {"krbprincipalaux", "krbTicketPolicyAux", NULL};
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf int p, q, r=0, amask=0;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if ((st=checkattributevalue(ld, (xargs.dn) ? xargs.dn : principal_dn,
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf "objectclass", attrvalues, &amask)) != 0)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf goto cleanup;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf memset(strval, 0, sizeof(strval));
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf for (p=1, q=0; p<=2; p<<=1, ++q) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if ((p & amask) == 0)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf strval[r++] = attrvalues[q];
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (r != 0) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if ((st=krb5_add_str_mem_ldap_mod(&mods, "objectclass", LDAP_MOD_ADD, strval)) != 0)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf goto cleanup;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (xargs.dn != NULL)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf st=ldap_modify_ext_s(ld, xargs.dn, mods, NULL, NULL);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf else
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf st = ldap_modify_ext_s(ld, principal_dn, mods, NULL, NULL);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (st != LDAP_SUCCESS) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf snprintf(errbuf, sizeof (errbuf), gettext("User modification failed: %s"), ldap_err2string(st));
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf st = translate_ldap_error (st, OP_MOD);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf krb5_set_error_message(context, st, "%s", errbuf);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf goto cleanup;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillfcleanup:
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (user)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf free(user);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf free_xargs(xargs);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (standalone_principal_dn)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf free(standalone_principal_dn);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (principal_dn)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf free (principal_dn);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf /* Solaris Kerberos: fix memleak */
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (ber_tl_data) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf int j;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf for (j = 0; ber_tl_data[j] != NULL; j++) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf free (ber_tl_data[j]->bv_val);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf free (ber_tl_data[j]);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf free(ber_tl_data);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (polname != NULL)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf free(polname);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (subtree)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf free (subtree);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (bersecretkey) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf for (l=0; bersecretkey[l]; ++l) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (bersecretkey[l]->bv_val)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf free (bersecretkey[l]->bv_val);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf free (bersecretkey[l]);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf free (bersecretkey);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf ldap_mods_free(mods, 1);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf krb5_ldap_put_handle_to_pool(ldap_context, ldap_server_handle);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf *nentries = i;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf return(st);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf}
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillfkrb5_error_code
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillfkrb5_read_tkt_policy (context, ldap_context, entries, policy)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf krb5_context context;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf krb5_ldap_context *ldap_context;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf krb5_db_entry *entries;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf char *policy;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf{
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf krb5_error_code st=0;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf unsigned int mask=0, omask=0;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf int tkt_mask=(KDB_MAX_LIFE_ATTR | KDB_MAX_RLIFE_ATTR | KDB_TKT_FLAGS_ATTR);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf krb5_ldap_policy_params *tktpoldnparam=NULL;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if ((st=krb5_get_attributes_mask(context, entries, &mask)) != 0)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf goto cleanup;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if ((mask & tkt_mask) == tkt_mask)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf goto cleanup;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (policy != NULL) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf st = krb5_ldap_read_policy(context, policy, &tktpoldnparam, &omask);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (st && st != KRB5_KDB_NOENTRY) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf prepend_err_str(context, gettext("Error reading ticket policy. "), st, st);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf goto cleanup;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf st = 0; /* reset the return status */
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if ((mask & KDB_MAX_LIFE_ATTR) == 0) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if ((omask & KDB_MAX_LIFE_ATTR) == KDB_MAX_LIFE_ATTR)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf entries->max_life = tktpoldnparam->maxtktlife;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf else if (ldap_context->lrparams->max_life)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf entries->max_life = ldap_context->lrparams->max_life;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if ((mask & KDB_MAX_RLIFE_ATTR) == 0) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if ((omask & KDB_MAX_RLIFE_ATTR) == KDB_MAX_RLIFE_ATTR)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf entries->max_renewable_life = tktpoldnparam->maxrenewlife;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf else if (ldap_context->lrparams->max_renewable_life)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf entries->max_renewable_life = ldap_context->lrparams->max_renewable_life;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if ((mask & KDB_TKT_FLAGS_ATTR) == 0) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if ((omask & KDB_TKT_FLAGS_ATTR) == KDB_TKT_FLAGS_ATTR)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf entries->attributes = tktpoldnparam->tktflags;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf else if (ldap_context->lrparams->tktflags)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf entries->attributes |= ldap_context->lrparams->tktflags;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf krb5_ldap_free_policy(context, tktpoldnparam);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillfcleanup:
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf return st;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf}
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillfkrb5_error_code
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillfkrb5_decode_krbsecretkey(context, entries, bvalues)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf krb5_context context;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf krb5_db_entry *entries;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf struct berval **bvalues;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf{
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf char *user=NULL;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf int i=0, j=0, noofkeys=0;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf krb5_key_data *key_data=NULL, *tmp;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf krb5_error_code st=0;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if ((st=krb5_unparse_name(context, entries->princ, &user)) != 0)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf goto cleanup;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf for (i=0; bvalues[i] != NULL; ++i) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf int mkvno; /* Not used currently */
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf krb5_int16 n_kd;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf krb5_key_data *kd;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf krb5_data in;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (bvalues[i]->bv_len == 0)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf continue;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf in.length = bvalues[i]->bv_len;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf in.data = bvalues[i]->bv_val;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf st = asn1_decode_sequence_of_keys (&in,
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf &kd,
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf &n_kd,
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf &mkvno);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (st != 0) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf const char *msg = error_message(st);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf st = -1; /* Something more appropriate ? */
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf krb5_set_error_message (context, st,
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf gettext("unable to decode stored principal key data (%s)"), msg);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf goto cleanup;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf noofkeys += n_kd;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf tmp = key_data;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf key_data = realloc (key_data, noofkeys * sizeof (krb5_key_data));
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (key_data == NULL) {
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf key_data = tmp;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf st = ENOMEM;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf goto cleanup;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf for (j = 0; j < n_kd; j++)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf key_data[noofkeys - n_kd + j] = kd[j];
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf free (kd);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf }
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf entries->n_key_data = noofkeys;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf entries->key_data = key_data;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillfcleanup:
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf ldap_value_free_len(bvalues);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf free (user);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf return st;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf}
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillfstatic char *
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillfgetstringtime(epochtime)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf krb5_timestamp epochtime;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf{
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf struct tm tme;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf char *strtime=NULL;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf time_t posixtime = epochtime;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf strtime = calloc (50, 1);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (strtime == NULL)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf return NULL;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf if (gmtime_r(&posixtime, &tme) == NULL)
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf return NULL;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf strftime(strtime, 50, DATE_FORMAT, &tme);
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf return strtime;
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf}
54925bf60766fbb4f1f2d7c843721406a7b7a3fbwillf