Blame src/lib/kadm5/unit-test/setkey-test.c

Packit fd8b60
/* -*- mode: c; c-basic-offset: 4; indent-tabs-mode: nil -*- */
Packit fd8b60
#include <k5-int.h>
Packit fd8b60
#include <kadm5/admin.h>
Packit fd8b60
Packit fd8b60
#if     HAVE_SRAND48
Packit fd8b60
#define RAND()          lrand48()
Packit fd8b60
#define SRAND(a)        srand48(a)
Packit fd8b60
#define RAND_TYPE       long
Packit fd8b60
#elif   HAVE_SRAND
Packit fd8b60
#define RAND()          rand()
Packit fd8b60
#define SRAND(a)        srand(a)
Packit fd8b60
#define RAND_TYPE       int
Packit fd8b60
#elif   HAVE_SRANDOM
Packit fd8b60
#define RAND()          random()
Packit fd8b60
#define SRAND(a)        srandom(a)
Packit fd8b60
#define RAND_TYPE       long
Packit fd8b60
#else   /* no random */
Packit fd8b60
need a random number generator
Packit fd8b60
#endif  /* no random */
Packit fd8b60
Packit fd8b60
krb5_keyblock test1[] = {
Packit fd8b60
    {0, ENCTYPE_AES128_CTS_HMAC_SHA1_96, 0, 0},
Packit fd8b60
    {-1},
Packit fd8b60
};
Packit fd8b60
krb5_keyblock test2[] = {
Packit fd8b60
    {0, ENCTYPE_AES128_CTS_HMAC_SHA1_96, 0, 0},
Packit fd8b60
    {-1},
Packit fd8b60
};
Packit fd8b60
krb5_keyblock test3[] = {
Packit fd8b60
    {0, ENCTYPE_AES128_CTS_HMAC_SHA1_96, 0, 0},
Packit fd8b60
    {-1},
Packit fd8b60
};
Packit fd8b60
Packit fd8b60
krb5_keyblock *tests[] = {
Packit fd8b60
    test1, test2, test3, NULL
Packit fd8b60
};
Packit fd8b60
Packit fd8b60
krb5_data tgtname = {
Packit fd8b60
    0,
Packit fd8b60
    KRB5_TGS_NAME_SIZE,
Packit fd8b60
    KRB5_TGS_NAME
Packit fd8b60
};
Packit fd8b60
Packit fd8b60
krb5_enctype ktypes[] = { 0, 0 };
Packit fd8b60
Packit fd8b60
extern krb5_kt_ops krb5_ktf_writable_ops;
Packit fd8b60
Packit fd8b60
int
Packit fd8b60
main(int argc, char **argv)
Packit fd8b60
{
Packit fd8b60
    krb5_context context;
Packit fd8b60
    krb5_keytab kt;
Packit fd8b60
    krb5_keytab_entry ktent;
Packit fd8b60
    krb5_encrypt_block eblock;
Packit fd8b60
    krb5_creds my_creds;
Packit fd8b60
    krb5_get_init_creds_opt *opt;
Packit fd8b60
    kadm5_principal_ent_rec princ_ent;
Packit fd8b60
    krb5_principal princ, server;
Packit fd8b60
    char pw[16];
Packit fd8b60
    char *whoami, *principal, *authprinc, *authpwd;
Packit fd8b60
    krb5_data pwdata;
Packit fd8b60
    void *handle;
Packit fd8b60
    int ret, test, encnum;
Packit fd8b60
    unsigned int i;
Packit fd8b60
Packit fd8b60
    whoami = argv[0];
Packit fd8b60
Packit fd8b60
    if (argc < 2 || argc > 4) {
Packit fd8b60
        fprintf(stderr, "Usage: %s principal [authuser] [authpwd]\n", whoami);
Packit fd8b60
        exit(1);
Packit fd8b60
    }
Packit fd8b60
    principal = argv[1];
Packit fd8b60
    authprinc = (argc > 2) ? argv[2] : argv[0];
Packit fd8b60
    authpwd = (argc > 3) ? argv[3] : NULL;
Packit fd8b60
Packit fd8b60
    /*
Packit fd8b60
     * Setup.  Initialize data structures, open keytab, open connection
Packit fd8b60
     * to kadm5 server.
Packit fd8b60
     */
Packit fd8b60
Packit fd8b60
    memset(&context, 0, sizeof(context));
Packit fd8b60
    kadm5_init_krb5_context(&context);
Packit fd8b60
Packit fd8b60
    ret = krb5_parse_name(context, principal, &princ);
Packit fd8b60
    if (ret) {
Packit fd8b60
        com_err(whoami, ret, "while parsing principal name %s", principal);
Packit fd8b60
        exit(1);
Packit fd8b60
    }
Packit fd8b60
Packit fd8b60
    if((ret = krb5_build_principal_ext(context, &server,
Packit fd8b60
                                       krb5_princ_realm(kcontext, princ)->length,
Packit fd8b60
                                       krb5_princ_realm(kcontext, princ)->data,
Packit fd8b60
                                       tgtname.length, tgtname.data,
Packit fd8b60
                                       krb5_princ_realm(kcontext, princ)->length,
Packit fd8b60
                                       krb5_princ_realm(kcontext, princ)->data,
Packit fd8b60
                                       0))) {
Packit fd8b60
        com_err(whoami, ret, "while building server name");
Packit fd8b60
        exit(1);
Packit fd8b60
    }
Packit fd8b60
Packit fd8b60
    ret = krb5_kt_default(context, &kt;;
Packit fd8b60
    if (ret) {
Packit fd8b60
        com_err(whoami, ret, "while opening keytab");
Packit fd8b60
        exit(1);
Packit fd8b60
    }
Packit fd8b60
Packit fd8b60
    ret = kadm5_init(context, authprinc, authpwd, KADM5_ADMIN_SERVICE, NULL,
Packit fd8b60
                     KADM5_STRUCT_VERSION, KADM5_API_VERSION_4, NULL,
Packit fd8b60
                     &handle);
Packit fd8b60
    if (ret) {
Packit fd8b60
        com_err(whoami, ret, "while initializing connection");
Packit fd8b60
        exit(1);
Packit fd8b60
    }
Packit fd8b60
Packit fd8b60
    /* these pw's don't need to be secure, just different every time */
Packit fd8b60
    SRAND((RAND_TYPE)time((void *) NULL));
Packit fd8b60
    pwdata.data = pw;
Packit fd8b60
    pwdata.length = sizeof(pw);
Packit fd8b60
Packit fd8b60
    /*
Packit fd8b60
     * For each test:
Packit fd8b60
     *
Packit fd8b60
     * For each enctype in the test, construct a random password/key.
Packit fd8b60
     * Assign all keys to principal with kadm5_setkey_principal.  Add
Packit fd8b60
     * each key to the keytab, and acquire an initial ticket with the
Packit fd8b60
     * keytab (XXX can I specify the kvno explicitly?).  If
Packit fd8b60
     * krb5_get_init_creds_keytab succeeds, then the keys were set
Packit fd8b60
     * successfully.
Packit fd8b60
     */
Packit fd8b60
    for (test = 0; tests[test] != NULL; test++) {
Packit fd8b60
        krb5_keyblock *testp = tests[test];
Packit fd8b60
        kadm5_key_data *extracted;
Packit fd8b60
        int n_extracted, match;
Packit fd8b60
        printf("+ Test %d:\n", test);
Packit fd8b60
Packit fd8b60
        for (encnum = 0; testp[encnum].magic != -1; encnum++) {
Packit fd8b60
            for (i = 0; i < sizeof(pw); i++)
Packit fd8b60
                pw[i] = (RAND() % 26) + '0'; /* XXX */
Packit fd8b60
Packit fd8b60
            krb5_use_enctype(context, &eblock, testp[encnum].enctype);
Packit fd8b60
            ret = krb5_string_to_key(context, &eblock, &testp[encnum],
Packit fd8b60
                                     &pwdata, NULL);
Packit fd8b60
            if (ret) {
Packit fd8b60
                com_err(whoami, ret, "while converting string to key");
Packit fd8b60
                exit(1);
Packit fd8b60
            }
Packit fd8b60
        }
Packit fd8b60
Packit fd8b60
        /* now, encnum == # of keyblocks in testp */
Packit fd8b60
        ret = kadm5_setkey_principal(handle, princ, testp, encnum);
Packit fd8b60
        if (ret) {
Packit fd8b60
            com_err(whoami, ret, "while setting keys");
Packit fd8b60
            exit(1);
Packit fd8b60
        }
Packit fd8b60
Packit fd8b60
        ret = kadm5_get_principal(handle, princ, &princ_ent, KADM5_KVNO);
Packit fd8b60
        if (ret) {
Packit fd8b60
            com_err(whoami, ret, "while retrieving principal");
Packit fd8b60
            exit(1);
Packit fd8b60
        }
Packit fd8b60
Packit fd8b60
        ret = kadm5_get_principal_keys(handle, princ, 0, &extracted,
Packit fd8b60
                                       &n_extracted);
Packit fd8b60
        if (ret) {
Packit fd8b60
            com_err(whoami, ret, "while extracting keys");
Packit fd8b60
            exit(1);
Packit fd8b60
        }
Packit fd8b60
Packit fd8b60
        for (encnum = 0; testp[encnum].magic != -1; encnum++) {
Packit fd8b60
            printf("+   enctype %d\n", testp[encnum].enctype);
Packit fd8b60
Packit fd8b60
            for (match = 0; match < n_extracted; match++) {
Packit fd8b60
                if (extracted[match].key.enctype == testp[encnum].enctype)
Packit fd8b60
                    break;
Packit fd8b60
            }
Packit fd8b60
            if (match >= n_extracted) {
Packit fd8b60
                com_err(whoami, KRB5_WRONG_ETYPE, "while matching enctypes");
Packit fd8b60
                exit(1);
Packit fd8b60
            }
Packit fd8b60
            if (extracted[match].key.length != testp[encnum].length ||
Packit fd8b60
                memcmp(extracted[match].key.contents, testp[encnum].contents,
Packit fd8b60
                       testp[encnum].length) != 0) {
Packit fd8b60
                com_err(whoami, KRB5_KDB_NO_MATCHING_KEY, "verifying keys");
Packit fd8b60
                exit(1);
Packit fd8b60
            }
Packit fd8b60
Packit fd8b60
            memset(&ktent, 0, sizeof(ktent));
Packit fd8b60
            ktent.principal = princ;
Packit fd8b60
            ktent.key = testp[encnum];
Packit fd8b60
            ktent.vno = princ_ent.kvno;
Packit fd8b60
Packit fd8b60
            ret = krb5_kt_add_entry(context, kt, &ktent);
Packit fd8b60
            if (ret) {
Packit fd8b60
                com_err(whoami, ret, "while adding keytab entry");
Packit fd8b60
                exit(1);
Packit fd8b60
            }
Packit fd8b60
Packit fd8b60
            memset(&my_creds, 0, sizeof(my_creds));
Packit fd8b60
            my_creds.client = princ;
Packit fd8b60
            my_creds.server = server;
Packit fd8b60
Packit fd8b60
            ktypes[0] = testp[encnum].enctype;
Packit fd8b60
            ret = krb5_get_init_creds_opt_alloc(context, &opt;;
Packit fd8b60
            if (ret) {
Packit fd8b60
                com_err(whoami, ret, "while allocating gic opts");
Packit fd8b60
                exit(1);
Packit fd8b60
            }
Packit fd8b60
            krb5_get_init_creds_opt_set_etype_list(opt, ktypes, 1);
Packit fd8b60
            ret = krb5_get_init_creds_keytab(context, &my_creds, princ,
Packit fd8b60
                                             kt, 0, NULL /* in_tkt_service */,
Packit fd8b60
                                             opt);
Packit fd8b60
            krb5_get_init_creds_opt_free(context, opt);
Packit fd8b60
            if (ret) {
Packit fd8b60
                com_err(whoami, ret, "while acquiring initial ticket");
Packit fd8b60
                exit(1);
Packit fd8b60
            }
Packit fd8b60
            krb5_free_cred_contents(context, &my_creds);
Packit fd8b60
Packit fd8b60
            /* since I can't specify enctype explicitly ... */
Packit fd8b60
            ret = krb5_kt_remove_entry(context, kt, &ktent);
Packit fd8b60
            if (ret) {
Packit fd8b60
                com_err(whoami, ret, "while removing keytab entry");
Packit fd8b60
                exit(1);
Packit fd8b60
            }
Packit fd8b60
        }
Packit fd8b60
Packit fd8b60
        (void)kadm5_free_kadm5_key_data(context, n_extracted, extracted);
Packit fd8b60
    }
Packit fd8b60
Packit fd8b60
    ret = krb5_kt_close(context, kt);
Packit fd8b60
    if (ret) {
Packit fd8b60
        com_err(whoami, ret, "while closing keytab");
Packit fd8b60
        exit(1);
Packit fd8b60
    }
Packit fd8b60
Packit fd8b60
    ret = kadm5_destroy(handle);
Packit fd8b60
    if (ret) {
Packit fd8b60
        com_err(whoami, ret, "while closing kadmin connection");
Packit fd8b60
        exit(1);
Packit fd8b60
    }
Packit fd8b60
Packit fd8b60
    krb5_free_principal(context, princ);
Packit fd8b60
    krb5_free_principal(context, server);
Packit fd8b60
    krb5_free_context(context);
Packit fd8b60
    return 0;
Packit fd8b60
}