krb5_cccol_cursor_free.rst
krb5_cccol_cursor_new.rst
krb5_cccol_cursor_next.rst
+ krb5_cccol_have_content.rst
krb5_cccol_last_change_time.rst
krb5_cccol_lock.rst
krb5_cccol_unlock.rst
krb5_error_code KRB5_CALLCONV
krb5_cccol_cursor_free(krb5_context context, krb5_cccol_cursor *cursor);
+/**
+ * Check if the credential cache collection contains any credentials.
+ *
+ * @param [in] context Library context
+ *
+ * @retval 0 Credentials are available in the collection
+ * @retval KRB5_CC_NOTFOUND The collection contains no credentials
+ */
+krb5_error_code KRB5_CALLCONV
+krb5_cccol_have_content(krb5_context context);
+
/**
* Return a timestamp of the last modification of any known credential cache.
*
*cache_out = cache;
return ret;
}
+
+krb5_error_code KRB5_CALLCONV
+krb5_cccol_have_content(krb5_context context)
+{
+ krb5_cccol_cursor col_cursor;
+ krb5_cc_cursor cache_cursor;
+ krb5_ccache cache;
+ krb5_creds creds;
+ krb5_boolean found = FALSE;
+
+ if (krb5_cccol_cursor_new(context, &col_cursor))
+ goto no_entries;
+
+ while (!found && !krb5_cccol_cursor_next(context, col_cursor, &cache) &&
+ cache != NULL) {
+ if (krb5_cc_start_seq_get(context, cache, &cache_cursor))
+ continue;
+ while (!found &&
+ !krb5_cc_next_cred(context, cache, &cache_cursor, &creds)) {
+ if (!krb5_is_config_principal(context, creds.client))
+ found = TRUE;
+ krb5_free_cred_contents(context, &creds);
+ }
+ krb5_cc_end_seq_get(context, cache, &cache_cursor);
+ krb5_cc_close(context, cache);
+ }
+ krb5_cccol_cursor_free(context, &col_cursor);
+ if (found)
+ return 0;
+
+no_entries:
+ krb5_set_error_message(context, KRB5_CC_NOTFOUND,
+ _("No Kerberos credentials available"));
+ return KRB5_CC_NOTFOUND;
+}
cursor_test('filemem', [fccname, mfoo, mbar], [fccname, mfoo, mbar])
cursor_test('dirmem', [dccname, mfoo], [duser, dalice, dbob, mfoo])
+# Test krb5_cccol_have_content.
+realm.run_as_client(['./t_cccursor', dccname, 'CONTENT'])
+realm.run_as_client(['./t_cccursor', fccname, 'CONTENT'])
+realm.run_as_client(['./t_cccursor', realm.ccache, 'CONTENT'])
+realm.run_as_client(['./t_cccursor', mfoo, 'CONTENT'], expected_code=1)
+
# Make sure FILE doesn't yield a nonexistent default cache.
realm.run_as_client([kdestroy])
cursor_test('noexist', [], [])
+realm.run_as_client(['./t_cccursor', fccname, 'CONTENT'], expected_code=1)
success('Renewing credentials')
* Displays a list of caches returned by the cccol cursor. The first argument,
* if given, is set to the default cache name for the context before iterating.
* Any remaining argments are resolved as caches and kept open during the
- * iteration.
+ * iteration. If the argument "CONTENT" is given as one of the cache names,
+ * immediately exit with status 0 if the collection contains credentials and 1
+ * if it does not.
*/
#include "k5-int.h"
if (argc > 2) {
assert(argc < 60);
- for (i = 2; i < argc; i++)
+ for (i = 2; i < argc; i++) {
+ if (strcmp(argv[i], "CONTENT") == 0)
+ return (krb5_cccol_have_content(ctx) != 0);
assert(krb5_cc_resolve(ctx, argv[i], &hold[i - 2]) == 0);
+ }
}
assert(krb5_cccol_cursor_new(ctx, &cursor) == 0);
krb5_cccol_cursor_free
krb5_cccol_cursor_new
krb5_cccol_cursor_next
+krb5_cccol_have_content
krb5_change_cache
krb5_change_password
krb5_check_clockskew
; new in 1.11 (note that 399-400 are used above)
krb5_chpw_message @398
krb5_kt_have_content @401
+ krb5_cccol_have_content @402