krb5_timestamp mod_date,
krb5_const_principal mod_princ);
+/*
+ * These are wrappers around realloc() and free(). Applications and KDB
+ * modules can use them when manipulating principal and policy entries to
+ * ensure that they allocate and free memory in a manner compatible with the
+ * library. Using libkrb5 or libkbd5 functions to construct values (such as
+ * krb5_copy_principal() to construct the princ field of a krb5_db_entry) is
+ * also safe. On Unix platforms, just using malloc() and free() is safe as
+ * long as the application or module does not use a malloc replacement.
+ */
void *krb5_db_alloc( krb5_context kcontext,
void *ptr,
size_t size );
-
void krb5_db_free( krb5_context kcontext,
void *ptr);
* The documentation in these comments describes the DAL as it is currently
* implemented and used, not as it should be. So if anything seems off, that
* probably means the current state of things is off.
+ *
+ * Modules must allocate memory for principal entries, policy entries, and
+ * other structures using an allocator compatible with malloc() as seen by
+ * libkdb5 and libkrb5. Modules may link against libkdb5 and call
+ * krb5_db_alloc() to be certain that the same malloc implementation is used.
*/
typedef struct _kdb_vftabl {
unsigned int flags,
krb5_db_entry **entry);
- /*
- * Mandatory: Free a database entry. The entry may have been constructed
- * by the caller (using the db_alloc function to allocate associated
- * memory); thus, a plugin must allocate each field of a principal entry
- * separately.
- */
- void (*free_principal)(krb5_context kcontext, krb5_db_entry *entry);
-
/*
* Optional: Create or modify a principal entry. db_args communicates
* command-line arguments for module-specific flags.
*/
krb5_error_code (*delete_policy)(krb5_context kcontext, char *policy);
- /* Optional: Free a policy entry returned by db_get_policy. */
- void (*free_policy)(krb5_context kcontext, osa_policy_ent_t val);
-
- /*
- * Mandatory: Has the semantics of realloc(ptr, size). Callers use this to
- * allocate memory for new or changed principal entries, so the module
- * should expect to potentially see this memory in db_free_principal.
- */
- void *(*alloc)(krb5_context kcontext, void *ptr, size_t size);
-
- /*
- * Mandatory: Has the semantics of free(ptr). Callers use this to free
- * fields from a principal entry (such as key data) before changing it in
- * place, and in some cases to free data they allocated with db_alloc.
- */
- void (*free)(krb5_context kcontext, void *ptr);
-
/*
* Optional with default: Retrieve a master keyblock from the stash file
* db_args, filling in *key and *kvno. mname is the name of the master
return 0;
}
+static void
+free_tl_data(krb5_tl_data *list)
+{
+ krb5_tl_data *next;
+
+ for (; list != NULL; list = next) {
+ next = list->tl_data_next;
+ free(list->tl_data_contents);
+ free(list);
+ }
+}
+
void
krb5_db_free_principal(krb5_context kcontext, krb5_db_entry *entry)
{
- krb5_error_code status = 0;
- kdb_vftabl *v;
+ int i;
- status = get_vftabl(kcontext, &v);
- if (status)
+ if (entry == NULL)
return;
- v->free_principal(kcontext, entry);
+ free(entry->e_data);
+ krb5_free_principal(kcontext, entry->princ);
+ free_tl_data(entry->tl_data);
+ for (i = 0; i < entry->n_key_data; i++)
+ krb5_dbe_free_key_data_contents(kcontext, &entry->key_data[i]);
+ free(entry->key_data);
+ free(entry);
}
static void
void *
krb5_db_alloc(krb5_context kcontext, void *ptr, size_t size)
{
- krb5_error_code status;
- kdb_vftabl *v;
-
- status = get_vftabl(kcontext, &v);
- if (status)
- return NULL;
- return v->alloc(kcontext, ptr, size);
+ return realloc(ptr, size);
}
void
krb5_db_free(krb5_context kcontext, void *ptr)
{
- krb5_error_code status;
- kdb_vftabl *v;
-
- status = get_vftabl(kcontext, &v);
- if (status)
- return;
- v->free(kcontext, ptr);
+ free(ptr);
}
/* has to be modified */
void
krb5_db_free_policy(krb5_context kcontext, osa_policy_ent_t policy)
{
- krb5_error_code status = 0;
- kdb_vftabl *v;
-
- status = get_vftabl(kcontext, &v);
- if (status || v->free_policy == NULL)
+ if (policy == NULL)
return;
- v->free_policy(kcontext, policy);
+ free(policy->name);
+ free(policy->allowed_keysalts);
+ free_tl_data(policy->tl_data);
+ free(policy);
}
krb5_error_code
unsigned int f,
krb5_db_entry **d),
(ctx, p, f, d));
-WRAP_VOID (krb5_db2_free_principal,
- (krb5_context ctx,
- krb5_db_entry *d),
- (ctx, d));
WRAP_K (krb5_db2_put_principal,
(krb5_context ctx,
krb5_db_entry *d,
WRAP_K (krb5_db2_delete_policy,
( krb5_context kcontext, char *policy ),
(kcontext, policy));
-WRAP_VOID (krb5_db2_free_policy,
- ( krb5_context kcontext, osa_policy_ent_t entry ),
- (kcontext, entry));
WRAP_K (krb5_db2_promote_db,
( krb5_context kcontext, char *conf_section, char **db_args ),
/* lock */ wrap_krb5_db2_lock,
/* unlock */ wrap_krb5_db2_unlock,
/* get_principal */ wrap_krb5_db2_get_principal,
- /* free_principal */ wrap_krb5_db2_free_principal,
/* put_principal */ wrap_krb5_db2_put_principal,
/* delete_principal */ wrap_krb5_db2_delete_principal,
/* rename_principal */ NULL,
/* put_policy */ wrap_krb5_db2_put_policy,
/* iter_policy */ wrap_krb5_db2_iter_policy,
/* delete_policy */ wrap_krb5_db2_delete_policy,
- /* free_policy */ wrap_krb5_db2_free_policy,
- /* alloc */ krb5_db2_alloc,
- /* free */ krb5_db2_free,
/* blah blah blah */ 0,0,0,0,0,
/* promote_db */ wrap_krb5_db2_promote_db,
0, 0, 0, 0,
return retval;
}
-/* Free an entry returned by krb5_db2_get_principal. */
-void
-krb5_db2_free_principal(krb5_context context, krb5_db_entry *entry)
-{
- krb5_dbe_free(context, entry);
-}
-
krb5_error_code
krb5_db2_put_principal(krb5_context context, krb5_db_entry *entry,
char **db_args)
}
retval = krb5_encode_princ_entry(context, &contdata, entry);
- krb5_dbe_free(context, entry);
+ krb5_db_free_principal(context, entry);
if (retval)
goto cleankey;
k5_mutex_unlock(krb5_db2_mutex);
retval = (*func)(func_arg, entry);
- krb5_dbe_free(ctx, entry);
+ krb5_db_free_principal(ctx, entry);
k5_mutex_lock(krb5_db2_mutex);
if (dbc->unlockiter) {
lockerr = curs_lock(curs);
return status;
}
-void *
-krb5_db2_alloc(krb5_context context, void *ptr, size_t size)
-{
- return realloc(ptr, size);
-}
-
-void
-krb5_db2_free(krb5_context context, void *ptr)
-{
- free(ptr);
-}
-
/* policy functions */
krb5_error_code
krb5_db2_create_policy(krb5_context context, osa_policy_ent_t policy)
krb5_error_code krb5_db2_get_age(krb5_context, char *, time_t *);
krb5_error_code krb5_db2_get_principal(krb5_context, krb5_const_principal,
unsigned int, krb5_db_entry **);
-void krb5_db2_free_principal(krb5_context, krb5_db_entry *);
krb5_error_code krb5_db2_put_principal(krb5_context, krb5_db_entry *,
char **db_args);
krb5_error_code krb5_db2_iterate(krb5_context, char *,
char **db_args);
const char *krb5_db2_err2str(krb5_context kcontext, long err_code);
-void *krb5_db2_alloc(krb5_context kcontext, void *ptr, size_t size);
-void krb5_db2_free(krb5_context kcontext, void *ptr);
/* policy management functions */
krb5_error_code krb5_db2_delete_policy(krb5_context kcontext, char *policy);
-void krb5_db2_free_policy(krb5_context kcontext, osa_policy_ent_t entry);
/* Thread-safety wrapper slapped on top of original implementation. */
extern k5_mutex_t *krb5_db2_mutex;
return 0;
error_out:
- krb5_dbe_free(context, entry);
+ krb5_db_free_principal(context, entry);
return retval;
}
-
-void
-krb5_dbe_free(krb5_context context, krb5_db_entry *entry)
-{
- krb5_tl_data * tl_data_next;
- krb5_tl_data * tl_data;
- int i, j;
-
- if (entry == NULL)
- return;
- free(entry->e_data);
- krb5_free_principal(context, entry->princ);
- for (tl_data = entry->tl_data; tl_data; tl_data = tl_data_next) {
- tl_data_next = tl_data->tl_data_next;
- free(tl_data->tl_data_contents);
- free(tl_data);
- }
- if (entry->key_data) {
- for (i = 0; i < entry->n_key_data; i++) {
- for (j = 0; j < entry->key_data[i].key_data_ver; j++) {
- if (entry->key_data[i].key_data_length[j]) {
- zapfree(entry->key_data[i].key_data_contents[j],
- entry->key_data[i].key_data_length[j]);
- }
- entry->key_data[i].key_data_contents[j] = NULL;
- entry->key_data[i].key_data_length[j] = 0;
- entry->key_data[i].key_data_type[j] = 0;
- }
- }
- free(entry->key_data);
- }
- free(entry);
-}
*pw_max_fail = policy->pw_max_fail;
*pw_failcnt_interval = policy->pw_failcnt_interval;
*pw_lockout_duration = policy->pw_lockout_duration;
- krb5_db2_free_policy(context, policy);
+ krb5_db_free_policy(context, policy);
}
}
/* lock */ krb5_ldap_lock,
/* unlock */ krb5_ldap_unlock,
/* get_principal */ krb5_ldap_get_principal,
- /* free_principal */ krb5_ldap_free_principal,
/* put_principal */ krb5_ldap_put_principal,
/* delete_principal */ krb5_ldap_delete_principal,
/* rename_principal */ krb5_ldap_rename_principal,
/* put_policy */ krb5_ldap_put_password_policy,
/* iter_policy */ krb5_ldap_iterate_password_policy,
/* delete_policy */ krb5_ldap_delete_password_policy,
- /* free_policy */ krb5_ldap_free_password_policy,
- /* alloc */ krb5_ldap_alloc,
- /* free */ krb5_ldap_free,
/* optional functions */
/* fetch_master_key */ NULL /* krb5_ldap_fetch_mkey */,
/* fetch_master_key_list */ NULL,
}
-void
-krb5_ldap_free_principal(krb5_context kcontext, krb5_db_entry *entry)
-{
- if (entry == NULL)
- return;
- krb5_dbe_free_contents(kcontext, entry);
- free(entry);
-}
-
krb5_error_code
krb5_ldap_iterate(krb5_context context, char *match_expr,
krb5_error_code (*func)(krb5_pointer, krb5_db_entry *),
if (DN)
free (DN);
- krb5_ldap_free_principal(context, entry);
+ krb5_db_free_principal(context, entry);
ldap_mods_free(mods, 1);
krb5_ldap_put_handle_to_pool(ldap_context, ldap_server_handle);
free(dn);
free(suser);
free(tuser);
- krb5_ldap_free_principal(context, entry);
+ krb5_db_free_principal(context, entry);
ldap_mods_free(mods, 1);
krb5_ldap_put_handle_to_pool(ldap_context, ldap_server_handle);
return st;
krb5_error_code
krb5_ldap_rename_principal(krb5_context context, krb5_const_principal source,
krb5_const_principal target);
-void
-krb5_ldap_free_principal(krb5_context, krb5_db_entry *);
krb5_error_code
krb5_ldap_iterate(krb5_context, char *,
cleanup:
ldap_msgfree(result);
- krb5_ldap_free_principal(context, entry);
+ krb5_db_free_principal(context, entry);
if (filter)
free (filter);
ldap_msgfree(result);
if (st != 0) {
if (*policy != NULL) {
- krb5_ldap_free_password_policy(context, *policy);
+ krb5_db_free_policy(context, *policy);
*policy = NULL;
}
}
goto cleanup;
(*func)(func_arg, entry);
- krb5_ldap_free_password_policy(context, entry);
+ krb5_db_free_policy(context, entry);
entry = NULL;
free(policy);
krb5_ldap_put_handle_to_pool(ldap_context, ldap_server_handle);
return st;
}
-
-void
-krb5_ldap_free_password_policy (context, entry)
- krb5_context context;
- osa_policy_ent_t entry;
-{
- if (entry) {
- free(entry->name);
- free(entry->allowed_keysalts);
- free(entry);
- }
- return;
-}
void (*)(krb5_pointer, osa_policy_ent_t),
krb5_pointer);
-void
-krb5_ldap_free_password_policy(krb5_context kcontext, osa_policy_ent_t entry);
-
#endif
krb5_ldap_get_principal
krb5_ldap_delete_principal
krb5_ldap_rename_principal
-krb5_ldap_free_principal
krb5_ldap_iterate
krb5_ldap_read_krbcontainer_dn
krb5_ldap_list_realm
krb5_ldap_put_password_policy
krb5_ldap_get_password_policy
krb5_ldap_delete_password_policy
-krb5_ldap_free_password_policy
krb5_ldap_iterate_password_policy
krb5_dbe_free_contents
krb5_ldap_free_server_params
krb5_ldap_free_server_context_params
-krb5_ldap_alloc
-krb5_ldap_free
krb5_ldap_delete_realm_1
krb5_ldap_lock
krb5_ldap_unlock
*pw_failcnt_interval = policy->pw_failcnt_interval;
*pw_lockout_duration = policy->pw_lockout_duration;
}
- krb5_ldap_free_password_policy(context, policy);
+ krb5_db_free_policy(context, policy);
}
xdrmem_create(&xdrs, NULL, 0, XDR_FREE);
return ret;
}
-static void
-test_free_principal(krb5_context context, krb5_db_entry *entry)
-{
- krb5_tl_data *tl, *next;
- int i, j;
-
- if (entry == NULL)
- return;
- free(entry->e_data);
- krb5_free_principal(context, entry->princ);
- for (tl = entry->tl_data; tl != NULL; tl = next) {
- next = tl->tl_data_next;
- free(tl->tl_data_contents);
- free(tl);
- }
- for (i = 0; i < entry->n_key_data; i++) {
- for (j = 0; j < entry->key_data[i].key_data_ver; j++) {
- if (entry->key_data[i].key_data_length[j]) {
- zapfree(entry->key_data[i].key_data_contents[j],
- entry->key_data[i].key_data_length[j]);
- }
- entry->key_data[i].key_data_contents[j] = NULL;
- entry->key_data[i].key_data_length[j] = 0;
- entry->key_data[i].key_data_type[j] = 0;
- }
- }
- free(entry->key_data);
- free(entry);
-}
-
-static void *
-test_alloc(krb5_context context, void *ptr, size_t size)
-{
- return realloc(ptr, size);
-}
-
-static void
-test_free(krb5_context context, void *ptr)
-{
- free(ptr);
-}
-
static krb5_error_code
test_fetch_master_key(krb5_context context, krb5_principal mname,
krb5_keyblock *key_out, krb5_kvno *kvno_out,
NULL, /* lock */
NULL, /* unlock */
test_get_principal,
- test_free_principal,
NULL, /* put_principal */
NULL, /* delete_principal */
NULL, /* rename_principal */
NULL, /* put_policy */
NULL, /* iter_policy */
NULL, /* delete_policy */
- NULL, /* free_policy */
- test_alloc,
- test_free,
test_fetch_master_key,
test_fetch_master_key_list,
NULL, /* store_master_key_list */