/*
 * snmpksm.c
 *
 * This code implements the Kerberos Security Model (KSM) for SNMP.
 *
 * Security number - 2066432
 */

#include <net-snmp/net-snmp-config.h>

#include <sys/types.h>
#if HAVE_WINSOCK_H
#include <winsock.h>
#endif
#include <stdio.h>
#ifdef HAVE_STDLIB_H
#include <stdlib.h>
#endif
#if TIME_WITH_SYS_TIME
# ifdef WIN32
#  include <sys/timeb.h>
# else
#  include <sys/time.h>
# endif
# include <time.h>
#else
# if HAVE_SYS_TIME_H
#  include <sys/time.h>
# else
#  include <time.h>
# endif
#endif
#if HAVE_STRING_H
#include <string.h>
#else
#include <strings.h>
#endif
#ifdef HAVE_NETINET_IN_H
#include <netinet/in.h>
#endif
#include <errno.h>


#if HAVE_DMALLOC_H
#include <dmalloc.h>
#endif

#ifdef NETSNMP_USE_KERBEROS_HEIMDAL
#ifndef NETSNMP_USE_KERBEROS_MIT
#define OLD_HEIMDAL
#endif 				/* ! NETSNMP_USE_KERBEROS_MIT */
#else
#define KRB5_DEPRECATED 1
#endif 				/* NETSNMP_USE_KERBEROS_HEIMDAL */

#ifdef NETSNMP_USE_KERBEROS_HEIMDAL
#define oid heimdal_oid_renamed
#endif				/* NETSNMP_USE_KERBEROS_HEIMDAL */
#include <krb5.h>
#ifdef NETSNMP_USE_KERBEROS_HEIMDAL
#undef oid
#endif				/* NETSNMP_USE_KERBEROS_HEIMDAL */

#ifdef NETSNMP_USE_KERBEROS_HEIMDAL
#define CHECKSUM_TYPE(x)	(x)->cksumtype
#define CHECKSUM_CONTENTS(x)	(x)->checksum.data
#define CHECKSUM_LENGTH(x)	(x)->checksum.length
#define TICKET_CLIENT(x)	(x)->client
#else				/* NETSNMP_USE_KERBEROS_HEIMDAL */
#define CHECKSUM_TYPE(x)	(x)->checksum_type
#define CHECKSUM_CONTENTS(x)	(x)->contents
#define CHECKSUM_LENGTH(x)	(x)->length
#define TICKET_CLIENT(x)	(x)->enc_part2->client
#endif				/* NETSNMP_USE_KERBEROS_HEIMDAL */

#include <net-snmp/output_api.h>
#include <net-snmp/config_api.h>
#include <net-snmp/utilities.h>

#include <net-snmp/library/asn1.h>
#include <net-snmp/library/snmp_api.h>
#include <net-snmp/library/callback.h>
#include <net-snmp/library/keytools.h>
#include <net-snmp/library/snmpv3.h>
#include <net-snmp/library/lcd_time.h>
#include <net-snmp/library/scapi.h>
#include <net-snmp/library/callback.h>
#include <net-snmp/library/snmp_secmod.h>
#include <net-snmp/library/snmpksm.h>

static krb5_context kcontext = NULL;
static krb5_rcache rcache = NULL;
static krb5_keytab keytab = NULL;
static int keytab_setup = 0;
static char *service_name = NULL;
static char service_host[] = "host";
static u_char null_id[] = {0};

static int      ksm_session_init(netsnmp_session *);
static void     ksm_free_state_ref(void *);
static int      ksm_free_pdu(netsnmp_pdu *);
static int      ksm_clone_pdu(netsnmp_pdu *, netsnmp_pdu *);

static int      ksm_insert_cache(long, krb5_auth_context, u_char *,
                                 size_t);
static void     ksm_decrement_ref_count(long);
static void     ksm_increment_ref_count(long);
static struct ksm_cache_entry *ksm_get_cache(long);

#define HASHSIZE	64

/*
 * Our information stored for the response PDU.
 */

struct ksm_secStateRef {
    krb5_auth_context auth_context;
    krb5_cksumtype  cksumtype;
};

/*
 * A KSM outgoing pdu cache entry
 */

struct ksm_cache_entry {
    long            msgid;
    int             refcount;
    krb5_auth_context auth_context;
    u_char         *secName;
    size_t          secNameLen;
    struct ksm_cache_entry *next;
};

/*
 * Poor man's hash table
 */

static struct ksm_cache_entry *ksm_hash_table[HASHSIZE];

/*
 * Stuff to deal with config values
 * Note the conditionals that wrap these--i don't know if these are
 * needed, since i don't know how library initialization and callbacks
 * and stuff work
 */

static int
init_snmpksm_post_config(int majorid, int minorid, void *serverarg,
			 void *clientarg)
{

    if (kcontext == NULL) {
	/* not reached, i'd imagine */
        return SNMPERR_KRB5;
    }

    if (service_name == NULL) {
	/* always reached, i'd imagine */
	char *c = netsnmp_ds_get_string(NETSNMP_DS_LIBRARY_ID,
					NETSNMP_DS_LIB_KSM_SERVICE_NAME);
	if (c != NULL) {
		service_name = c;
	}
	else {
		service_name = service_host;
	}
    }

    if (keytab_setup == 0) {
	/* always reached, i'd imagine */
	char *c = netsnmp_ds_get_string(NETSNMP_DS_LIBRARY_ID,
					NETSNMP_DS_LIB_KSM_KEYTAB);
	if (c) {
	    krb5_error_code retval;
	    DEBUGMSGTL(("ksm", "Using keytab %s\n", c));
	    retval = krb5_kt_resolve(kcontext, c, &keytab);
	    if (retval) {
		DEBUGMSGTL(("ksm", "krb5_kt_resolve(\"%s\") failed. KSM "
			    "config callback failing\n", error_message(retval)));
		return SNMPERR_KRB5;
	    }
	}
	else {
	    DEBUGMSGTL(("ksm", "Using default keytab\n"));
	}
	keytab_setup = 1;
    }

    return SNMPERR_SUCCESS;
}

/*
 * Initialize all of the state required for Kerberos (right now, just call
 * krb5_init_context).
 */

void
init_ksm(void)
{
    krb5_error_code retval;
    struct snmp_secmod_def *def;
    int             i;

    netsnmp_ds_register_config(ASN_OCTET_STR, "snmp", "defKSMKeytab",
                               NETSNMP_DS_LIBRARY_ID, NETSNMP_DS_LIB_KSM_KEYTAB);
    netsnmp_ds_register_config(ASN_OCTET_STR, "snmp", "defKSMServiceName",
                               NETSNMP_DS_LIBRARY_ID,
			       NETSNMP_DS_LIB_KSM_SERVICE_NAME);
    snmp_register_callback(SNMP_CALLBACK_LIBRARY,
			   SNMP_CALLBACK_POST_READ_CONFIG,
			   init_snmpksm_post_config, NULL);


    if (kcontext == NULL) {
        retval = krb5_init_context(&kcontext);

        if (retval) {
            DEBUGMSGTL(("ksm", "krb5_init_context failed (%s), not "
                        "registering KSM\n", error_message(retval)));
            return;
        }
    }

    for (i = 0; i < HASHSIZE; i++)
        ksm_hash_table[i] = NULL;

    def = SNMP_MALLOC_STRUCT(snmp_secmod_def);

    if (!def) {
        DEBUGMSGTL(("ksm", "Unable to malloc snmp_secmod struct, not "
                    "registering KSM\n"));
        return;
    }

    def->encode_reverse = ksm_rgenerate_out_msg;
    def->decode = ksm_process_in_msg;
    def->session_open = ksm_session_init;
    def->pdu_free_state_ref = ksm_free_state_ref;
    def->pdu_free = ksm_free_pdu;
    def->pdu_clone = ksm_clone_pdu;

    register_sec_mod(NETSNMP_KSM_SECURITY_MODEL, "ksm", def);
}

/*
 * These routines implement a simple cache for information we need to
 * process responses.  When we send out a request, it contains an AP_REQ;
 * we get back an AP_REP, and we need the authorization context from the
 * AP_REQ to decrypt the AP_REP.  But because right now there's nothing
 * that gets preserved across calls to rgenerate_out_msg to process_in_msg,
 * we cache these internally based on the message ID (we also cache the
 * passed-in security name, for reasons that are mostly stupid).
 */

static int
ksm_insert_cache(long msgid, krb5_auth_context auth_context,
                 u_char * secName, size_t secNameLen)
{
    struct ksm_cache_entry *entry;
    int             bucket;

    entry = SNMP_MALLOC_STRUCT(ksm_cache_entry);
    if (!entry)
        return SNMPERR_MALLOC;

    entry->msgid = msgid;
    entry->auth_context = auth_context;
    entry->refcount = 1;
    entry->secName = netsnmp_memdup(secName, secNameLen);
    if (secName && !entry->secName) {
        free(entry);
        return SNMPERR_GENERR;
    }

    entry->secNameLen = secNameLen;

    bucket = msgid % HASHSIZE;

    entry->next = ksm_hash_table[bucket];
    ksm_hash_table[bucket] = entry;

    return SNMPERR_SUCCESS;
}

static struct ksm_cache_entry *
ksm_get_cache(long msgid)
{
    struct ksm_cache_entry *entry;
    int             bucket;

    bucket = msgid % HASHSIZE;

    for (entry = ksm_hash_table[bucket]; entry != NULL;
         entry = entry->next)
        if (entry->msgid == msgid)
            return entry;

    return NULL;
}

static void
ksm_decrement_ref_count(long msgid)
{
    struct ksm_cache_entry *entry, *entry1;
    int             bucket;

    bucket = msgid % HASHSIZE;

    if (ksm_hash_table[bucket] && ksm_hash_table[bucket]->msgid == msgid) {
        entry = ksm_hash_table[bucket];

        /*
         * If the reference count is zero, then free it
         */

        if (--entry->refcount <= 0) {
            DEBUGMSGTL(("ksm", "Freeing entry for msgid %ld\n", msgid));
            krb5_auth_con_free(kcontext, entry->auth_context);
            free(entry->secName);
            ksm_hash_table[bucket] = entry->next;
            free(entry);
        }

        return;

    } else if (ksm_hash_table[bucket])
        for (entry1 = ksm_hash_table[bucket], entry = entry1->next;
             entry != NULL; entry1 = entry, entry = entry->next)
            if (entry->msgid == msgid) {

                if (--entry->refcount <= 0) {
                    DEBUGMSGTL(("ksm", "Freeing entry for msgid %ld\n",
                                msgid));
                    krb5_auth_con_free(kcontext, entry->auth_context);
                    free(entry->secName);
                    entry1->next = entry->next;
                    free(entry);
                }

                return;
            }

    DEBUGMSGTL(("ksm",
                "KSM: Unable to decrement cache entry for msgid %ld.\n",
                msgid));
}

static void
ksm_increment_ref_count(long msgid)
{
    struct ksm_cache_entry *entry = ksm_get_cache(msgid);

    if (!entry) {
        DEBUGMSGTL(("ksm", "Unable to find cache entry for msgid %ld "
                    "for increment\n", msgid));
        return;
    }

    entry->refcount++;
}

/*
 * Initialize specific session information (right now, just set up things to
 * not do an engineID probe)
 */

static int
ksm_session_init(netsnmp_session * sess)
{
    DEBUGMSGTL(("ksm",
                "KSM: Reached our session initialization callback\n"));

    sess->flags |= SNMP_FLAGS_DONT_PROBE;

    return SNMPERR_SUCCESS;
}

/*
 * Free our state information (this is only done on the agent side)
 */

static void
ksm_free_state_ref(void *ptr)
{
    struct ksm_secStateRef *ref = (struct ksm_secStateRef *) ptr;

    DEBUGMSGTL(("ksm", "KSM: Freeing state reference\n"));

    krb5_auth_con_free(kcontext, ref->auth_context);

    free(ref);
}

/*
 * This is called when the PDU is freed; this will decrement reference counts
 * for entries in our state cache.
 */

static int
ksm_free_pdu(netsnmp_pdu *pdu)
{
    ksm_decrement_ref_count(pdu->msgid);

    DEBUGMSGTL(("ksm", "Decrementing cache entry for PDU msgid %ld\n",
                pdu->msgid));

    return SNMPERR_SUCCESS;
}

/*
 * This is called when a PDU is cloned (to increase reference counts)
 */

static int
ksm_clone_pdu(netsnmp_pdu *pdu, netsnmp_pdu *pdu2)
{
    ksm_increment_ref_count(pdu->msgid);

    DEBUGMSGTL(("ksm", "Incrementing cache entry for PDU msgid %ld\n",
                pdu->msgid));

    return SNMPERR_SUCCESS;
}

/****************************************************************************
 *
 * ksm_generate_out_msg
 *
 * Parameters:
 *	(See list below...)
 *
 * Returns:
 *	SNMPERR_GENERIC                        On success.
 *	SNMPERR_KRB5
 *	... and others
 *
 *
 * Generate an outgoing message.
 *
 ****************************************************************************/

int
ksm_rgenerate_out_msg(struct snmp_secmod_outgoing_params *parms)
{
    krb5_auth_context auth_context = NULL;
    krb5_error_code retcode;
    krb5_ccache     cc = NULL;
    int             retval = SNMPERR_SUCCESS;
    krb5_data       outdata, ivector;
    krb5_keyblock  *subkey = NULL;
#ifdef NETSNMP_USE_KERBEROS_MIT
    krb5_data       input;
    krb5_enc_data   output;
    unsigned int    numcksumtypes;
    krb5_cksumtype  *cksumtype_array;
#elif defined OLD_HEIMDAL	/* NETSNMP_USE_KERBEROS_MIT */
    krb5_crypto heim_crypto = NULL;
#else                           /* NETSNMP_USE_KERBEROS_MIT */
    krb5_encrypt_block eblock;
#endif                          /* NETSNMP_USE_KERBEROS_MIT */
    size_t          blocksize, encrypted_length;
    unsigned char  *encrypted_data = NULL;
    long            zero = 0, tmp;
    int             i;
    u_char         *cksum_pointer;
    krb5_cksumtype  cksumtype;
    krb5_checksum   pdu_checksum;
    u_char         **wholeMsg = parms->wholeMsg;
    size_t	   *offset = parms->wholeMsgOffset, seq_offset;
    struct ksm_secStateRef *ksm_state = (struct ksm_secStateRef *)
        parms->secStateRef;
#ifdef OLD_HEIMDAL
    krb5_data encrypted_scoped_pdu;
#endif				/* OLD_HEIMDAL */
    int rc;
    char *colon = NULL;

    DEBUGMSGTL(("ksm", "Starting KSM processing\n"));

    outdata.length = 0;
    outdata.data = NULL;
    ivector.length = 0;
    ivector.data = NULL;
    CHECKSUM_CONTENTS(&pdu_checksum) = NULL;

    if (!ksm_state) {
        /*
         * If we've got a port number as part of the "peername", then
         * suppress this (temporarily) while we build the credential info.
         *   XXX - what about "udp:host" style addresses?
         */
        colon = strrchr(parms->session->peername, ':');
        if (colon != NULL) {
            *colon='\0';
        }

        /*
         * If we don't have a ksm_state, then we're a request.  Get a
         * credential cache and build a ap_req.
         */
        retcode = krb5_cc_default(kcontext, &cc);

        if (retcode) {
            DEBUGMSGTL(("ksm", "KSM: krb5_cc_default failed: %s\n",
                        error_message(retcode)));
            snmp_set_detail(error_message(retcode));
            retval = SNMPERR_KRB5;
            goto error;
        }

        DEBUGMSGTL(("ksm", "KSM: Set credential cache successfully\n"));

        /*
         * This seems odd, since we don't need this until later (or earlier,
         * depending on how you look at it), but because the most likely
         * errors are Kerberos at this point, I'll get this now to save
         * time not encoding the rest of the packet.
         *
         * Also, we need the subkey to encrypt the PDU (if required).
         */

        retcode =
            krb5_mk_req(kcontext, &auth_context,
                        AP_OPTS_MUTUAL_REQUIRED | AP_OPTS_USE_SUBKEY,
                        service_name, parms->session->peername, NULL,
                        cc, &outdata);

        if (colon != NULL)
            *colon=':';

        if (retcode) {
            DEBUGMSGTL(("ksm", "KSM: krb5_mk_req failed: %s\n",
                        error_message(retcode)));
            snmp_set_detail(error_message(retcode));
            retval = SNMPERR_KRB5;
            goto error;
        }

	DEBUGMSGTL(("ksm", "KSM: ticket retrieved successfully for \"%s/%s\" "
		    "(may not be actual ticket sname)\n", service_name,
		    parms->session->peername));

    } else {

        /*
         * Grab the auth_context from our security state reference
         */

        auth_context = ksm_state->auth_context;

        /*
         * Bundle up an AP_REP.  Note that we do this only when we
         * have a security state reference (which means we're in an agent
         * and we're sending a response).
         */

        DEBUGMSGTL(("ksm", "KSM: Starting reply processing.\n"));

        retcode = krb5_mk_rep(kcontext, auth_context, &outdata);

        if (retcode) {
            DEBUGMSGTL(("ksm", "KSM: krb5_mk_rep failed: %s\n",
                        error_message(retcode)));
            snmp_set_detail(error_message(retcode));
            retval = SNMPERR_KRB5;
            goto error;
        }

        DEBUGMSGTL(("ksm", "KSM: Finished with krb5_mk_rep()\n"));
    }

    /*
     * If we have to encrypt the PDU, do that now
     */

    if (parms->secLevel == SNMP_SEC_LEVEL_AUTHPRIV) {

        DEBUGMSGTL(("ksm", "KSM: Starting PDU encryption.\n"));

        /*
         * It's weird -
         *
         * If we're on the manager, it's a local subkey (because that's in
         * our AP_REQ)
         *
         * If we're on the agent, it's a remote subkey (because that comes
         * FROM the received AP_REQ).
         */

        if (ksm_state)
            retcode = krb5_auth_con_getremotesubkey(kcontext, auth_context,
                                                    &subkey);
        else
            retcode = krb5_auth_con_getlocalsubkey(kcontext, auth_context,
                                                   &subkey);

        if (retcode) {
            DEBUGMSGTL(("ksm",
                        "KSM: krb5_auth_con_getlocalsubkey failed: %s\n",
                        error_message(retcode)));
            snmp_set_detail(error_message(retcode));
            retval = SNMPERR_KRB5;
            goto error;
        }

        /*
         * Note that here we need to handle different things between the
         * old and new crypto APIs.  First, we need to get the final encrypted
         * length of the PDU.
         */

#ifdef NETSNMP_USE_KERBEROS_MIT
        retcode = krb5_c_encrypt_length(kcontext, subkey->enctype,
                                        parms->scopedPduLen,
                                        &encrypted_length);

        if (retcode) {
            DEBUGMSGTL(("ksm",
                        "Encryption length calculation failed: %s\n",
                        error_message(retcode)));
            snmp_set_detail(error_message(retcode));
            retval = SNMPERR_KRB5;
            goto error;
        }
#elif defined OLD_HEIMDAL
	retcode = krb5_crypto_init(kcontext, subkey, 0, &heim_crypto);
        if (retcode) {
            DEBUGMSGTL(("ksm", "krb5_crypto_init failed: %s\n",
                        error_message(retcode)));
            snmp_set_detail(error_message(retcode));
            retval = SNMPERR_KRB5;
            goto error;
        }
	encrypted_length = krb5_get_wrapped_length(kcontext, heim_crypto,
						   parms->scopedPduLen);
#else                           /* NETSNMP_USE_KERBEROS_MIT */

        krb5_use_enctype(kcontext, &eblock, subkey->enctype);
        retcode = krb5_process_key(kcontext, &eblock, subkey);

        if (retcode) {
            DEBUGMSGTL(("ksm", "krb5_process_key failed: %s\n",
                        error_message(retcode)));
            snmp_set_detail(error_message(retcode));
            retval = SNMPERR_KRB5;
            goto error;
        }

        encrypted_length = krb5_encrypt_size(parms->scopedPduLen,
                                             eblock.crypto_entry);
#endif                          /* NETSNMP_USE_KERBEROS_MIT */

#ifndef OLD_HEIMDAL /* since heimdal allocs the space for us */
        encrypted_data = malloc(encrypted_length);

        if (!encrypted_data) {
            DEBUGMSGTL(("ksm",
                        "KSM: Unable to malloc %d bytes for encrypt "
                        "buffer: %s\n", (int)parms->scopedPduLen,
                        strerror(errno)));
            retval = SNMPERR_MALLOC;
#ifndef NETSNMP_USE_KERBEROS_MIT
            krb5_finish_key(kcontext, &eblock);
#endif                          /* ! NETSNMP_USE_KERBEROS_MIT */

            goto error;
        }
#endif /* ! OLD_HEIMDAL */

        /*
         * We need to set up a blank initialization vector for the encryption.
         * Use a block of all zero's (which is dependent on the block size
         * of the encryption method).
         */

#ifdef NETSNMP_USE_KERBEROS_MIT

        retcode = krb5_c_block_size(kcontext, subkey->enctype, &blocksize);

        if (retcode) {
            DEBUGMSGTL(("ksm",
                        "Unable to determine crypto block size: %s\n",
                        error_message(retcode)));
            snmp_set_detail(error_message(retcode));
            retval = SNMPERR_KRB5;
            goto error;
        }
#elif defined (OLD_HEIMDAL)	/* NETSNMP_USE_KERBEROS_MIT */
#else                           /* NETSNMP_USE_KERBEROS_MIT */

        blocksize =
            krb5_enctype_array[subkey->enctype]->system->block_length;

#endif                          /* NETSNMP_USE_KERBEROS_MIT */

#ifndef OLD_HEIMDAL	/* since allocs the space for us */
        ivector.data = malloc(blocksize);

        if (!ivector.data) {
            DEBUGMSGTL(("ksm", "Unable to allocate %d bytes for ivector\n",
                        (int)blocksize));
            retval = SNMPERR_MALLOC;
            goto error;
        }

        ivector.length = blocksize;
        memset(ivector.data, 0, blocksize);
#endif /* OLD_HEIMDAL */

        /*
         * Finally!  Do the encryption!
         */

#ifdef NETSNMP_USE_KERBEROS_MIT

        input.data = (char *) parms->scopedPdu;
        input.length = parms->scopedPduLen;
        output.ciphertext.data = (char *) encrypted_data;
        output.ciphertext.length = encrypted_length;

        retcode =
            krb5_c_encrypt(kcontext, subkey, KSM_KEY_USAGE_ENCRYPTION,
                           &ivector, &input, &output);

#elif defined OLD_HEIMDAL /* NETSNMP_USE_KERBEROS_MIT */

	krb5_data_zero(&encrypted_scoped_pdu);
	retcode = krb5_encrypt(kcontext, heim_crypto, KSM_KEY_USAGE_ENCRYPTION,
			       parms->scopedPdu, parms->scopedPduLen,
			       &encrypted_scoped_pdu);
	if (retcode == 0) {
		encrypted_length = encrypted_scoped_pdu.length;
		encrypted_data = encrypted_scoped_pdu.data;
		krb5_data_zero(&encrypted_scoped_pdu);
	}
#else                           /* NETSNMP_USE_KERBEROS_MIT */

        retcode = krb5_encrypt(kcontext, (krb5_pointer) parms->scopedPdu,
                               (krb5_pointer) encrypted_data,
                               parms->scopedPduLen, &eblock, ivector.data);

        krb5_finish_key(kcontext, &eblock);

#endif                          /* NETSNMP_USE_KERBEROS_MIT */

        if (retcode) {
            DEBUGMSGTL(("ksm", "KSM: krb5_encrypt failed: %s\n",
                        error_message(retcode)));
            retval = SNMPERR_KRB5;
            snmp_set_detail(error_message(retcode));
            goto error;
        }

	*offset = 0;

        rc = asn_realloc_rbuild_string(wholeMsg, parms->wholeMsgLen,
                                             offset, 1,
                                             (u_char) (ASN_UNIVERSAL |
                                                       ASN_PRIMITIVE |
                                                       ASN_OCTET_STR),
                                             encrypted_data,
                                             encrypted_length);

        if (rc == 0) {
            DEBUGMSGTL(("ksm", "Building encrypted payload failed.\n"));
            retval = SNMPERR_TOO_LONG;
            goto error;
        }

        DEBUGMSGTL(("ksm", "KSM: Encryption complete.\n"));

    } else {
        /*
         * Plaintext PDU (not encrypted)
         */

        if (*parms->wholeMsgLen < parms->scopedPduLen) {
            DEBUGMSGTL(("ksm", "Not enough room for plaintext PDU.\n"));
            retval = SNMPERR_TOO_LONG;
            goto error;
        }
    }

    /*
     * Start encoding the msgSecurityParameters
     *
     * For now, use 0 for the response hint
     */

    DEBUGMSGTL(("ksm", "KSM: scopedPdu added to payload\n"));

    seq_offset = *offset;

    rc = asn_realloc_rbuild_int(wholeMsg, parms->wholeMsgLen,
                                      offset, 1,
                                      (u_char) (ASN_UNIVERSAL |
                                                ASN_PRIMITIVE |
                                                ASN_INTEGER),
                                      (long *) &zero, sizeof(zero));

    if (rc == 0) {
        DEBUGMSGTL(("ksm", "Building ksm security parameters failed.\n"));
        retval = SNMPERR_TOO_LONG;
        goto error;
    }

    rc = asn_realloc_rbuild_string(wholeMsg, parms->wholeMsgLen,
                                         offset, 1,
                                         (u_char) (ASN_UNIVERSAL |
                                                   ASN_PRIMITIVE |
                                                   ASN_OCTET_STR),
                                         (u_char *) outdata.data,
                                         outdata.length);

    if (rc == 0) {
        DEBUGMSGTL(("ksm", "Building ksm AP_REQ failed.\n"));
        retval = SNMPERR_TOO_LONG;
        goto error;
    }

    /*
     * If we didn't encrypt the packet, we haven't yet got the subkey.
     * Get that now.
     */

    if (!subkey) {
        if (ksm_state)
            retcode = krb5_auth_con_getremotesubkey(kcontext, auth_context,
                                                    &subkey);
        else
            retcode = krb5_auth_con_getlocalsubkey(kcontext, auth_context,
                                                   &subkey);
        if (retcode) {
            DEBUGMSGTL(("ksm", "krb5_auth_con_getlocalsubkey failed: %s\n",
                        error_message(retcode)));
            snmp_set_detail(error_message(retcode));
            retval = SNMPERR_KRB5;
            goto error;
        }
#ifdef OLD_HEIMDAL
	 retcode = krb5_crypto_init(kcontext, subkey, 0, &heim_crypto);
        if (retcode) {
            DEBUGMSGTL(("ksm", "krb5_crypto_init failed: %s\n",
                        error_message(retcode)));
            snmp_set_detail(error_message(retcode));
            retval = SNMPERR_KRB5;
            goto error;
        }
#endif					/* OLD_HEIMDAL */
    }

    /*
     * Now, we need to pick the "right" checksum algorithm.  For old
     * crypto, just pick CKSUMTYPE_RSA_MD5_DES; for new crypto, pick
     * one of the "approved" ones.
     */

#ifdef NETSNMP_USE_KERBEROS_MIT
    retcode = krb5_c_keyed_checksum_types(kcontext, subkey->enctype,
                                          &numcksumtypes, &cksumtype_array);

    if (retcode) {
	DEBUGMSGTL(("ksm", "Unable to find appropriate keyed checksum: %s\n",
		    error_message(retcode)));
	snmp_set_detail(error_message(retcode));
        retval = SNMPERR_KRB5;
        goto error;
    }

    if (numcksumtypes <= 0) {
	DEBUGMSGTL(("ksm", "We received a list of zero cksumtypes for this "
		    "enctype (%d)\n", subkey->enctype));
	snmp_set_detail("No valid checksum type for this encryption type");
	retval = SNMPERR_KRB5;
	goto error;
    }

    /*
     * It's not clear to me from the API which checksum you're supposed
     * to support, so I'm taking a guess at the first one
     */

    cksumtype = cksumtype_array[0];

    krb5_free_cksumtypes(kcontext, cksumtype_array);

    DEBUGMSGTL(("ksm", "KSM: Choosing checksum type of %d (subkey type "
		"of %d)\n", cksumtype, subkey->enctype));

    retcode = krb5_c_checksum_length(kcontext, cksumtype, &blocksize);

    if (retcode) {
        DEBUGMSGTL(("ksm", "Unable to determine checksum length: %s\n",
                    error_message(retcode)));
        snmp_set_detail(error_message(retcode));
        retval = SNMPERR_KRB5;
        goto error;
    }

    CHECKSUM_LENGTH(&pdu_checksum) = blocksize;

#else /* NETSNMP_USE_KERBEROS_MIT */
    if (ksm_state)
        cksumtype = ksm_state->cksumtype;
    else
#ifdef OLD_HEIMDAL
    {
	    /* no way to tell what kind of checksum to use without trying */
	    retval = krb5_create_checksum(kcontext, heim_crypto, 
					  KSM_KEY_USAGE_CHECKSUM, 0,
					  parms->scopedPdu, parms->scopedPduLen,
					  &pdu_checksum);
	    if (retval) {
		    DEBUGMSGTL(("ksm", "Unable to create a checksum: %s\n",
				error_message(retval)));
		    snmp_set_detail(error_message(retcode));
		    retval = SNMPERR_KRB5;
		    goto error;
	    }
	    cksumtype = CHECKSUM_TYPE(&pdu_checksum);
    }
#else					/* OLD_HEIMDAL */
	cksumtype = CKSUMTYPE_RSA_MD5_DES;
#endif					/* OLD_HEIMDAL */

#ifdef OLD_HEIMDAL
	if (!krb5_checksum_is_keyed(kcontext, cksumtype)) {
#else 				/* OLD_HEIMDAL */
    if (!is_keyed_cksum(cksumtype)) {
#endif 				/* OLD_HEIMDAL */
        DEBUGMSGTL(("ksm", "Checksum type %d is not a keyed checksum\n",
                    cksumtype));
        snmp_set_detail("Checksum is not a keyed checksum");
        retval = SNMPERR_KRB5;
        goto error;
    }

#ifdef OLD_HEIMDAL
    if (!krb5_checksum_is_collision_proof(kcontext, cksumtype)) {
#else 				/* OLD_HEIMDAL */
    if (!is_coll_proof_cksum(cksumtype)) {
#endif 				/* OLD_HEIMDAL */
        DEBUGMSGTL(("ksm", "Checksum type %d is not a collision-proof "
                    "checksum\n", cksumtype));
        snmp_set_detail("Checksum is not a collision-proof checksum");
        retval = SNMPERR_KRB5;
        goto error;
    }

#ifdef OLD_HEIMDAL
    if (CHECKSUM_CONTENTS(&pdu_checksum) != NULL ) {
	/* we did the bogus checksum--don't need to ask for the size again
	 * or initialize cksumtype; just free the bits */
	free(CHECKSUM_CONTENTS(&pdu_checksum));
	CHECKSUM_CONTENTS(&pdu_checksum) = NULL;
    }
    else {
	retval = krb5_checksumsize(kcontext, cksumtype,
				   &CHECKSUM_LENGTH(&pdu_checksum));
	if (retval) {
	    DEBUGMSGTL(("ksm", "Unable to determine checksum length: %s\n",
			error_message(retval)));
	    snmp_set_detail(error_message(retcode));
	    retval = SNMPERR_KRB5;
	    goto error;
	}
#else			/* OLD_HEIMDAL */
    CHECKSUM_LENGTH(&pdu_checksum) = krb5_checksum_size(kcontext, cksumtype);
#endif			/* OLD_HEIMDAL */
    CHECKSUM_TYPE(&pdu_checksum) = cksumtype;
#ifdef OLD_HEIMDAL
    }
#endif			/* OLD_HEIMDAL */

#endif /* NETSNMP_USE_KERBEROS_MIT */

    /*
     * Note that here, we're just leaving blank space for the checksum;
     * we remember where that is, and we'll fill it in later.
     */

    *offset += CHECKSUM_LENGTH(&pdu_checksum);
    memset(*wholeMsg + *parms->wholeMsgLen - *offset, 0, CHECKSUM_LENGTH(&pdu_checksum));

    cksum_pointer = *wholeMsg + *parms->wholeMsgLen - *offset;

    rc = asn_realloc_rbuild_header(wholeMsg, parms->wholeMsgLen,
                                         parms->wholeMsgOffset, 1,
                                         (u_char) (ASN_UNIVERSAL |
                                                   ASN_PRIMITIVE |
                                                   ASN_OCTET_STR),
                                         CHECKSUM_LENGTH(&pdu_checksum));

    if (rc == 0) {
        DEBUGMSGTL(("ksm", "Building ksm security parameters failed.\n"));
        retval = SNMPERR_TOO_LONG;
        goto error;
    }

    tmp = cksumtype;
    rc = asn_realloc_rbuild_int(wholeMsg, parms->wholeMsgLen,
                                      parms->wholeMsgOffset, 1,
                                      (u_char) (ASN_UNIVERSAL |
                                                ASN_PRIMITIVE |
                                                ASN_INTEGER),
                                      &tmp, sizeof(tmp));

    if (rc == 0) {
        DEBUGMSGTL(("ksm", "Building ksm security parameters failed.\n"));
        retval = SNMPERR_TOO_LONG;
        goto error;
    }

    rc = asn_realloc_rbuild_sequence(wholeMsg, parms->wholeMsgLen,
                                           parms->wholeMsgOffset, 1,
                                           (u_char) (ASN_SEQUENCE |
                                                     ASN_CONSTRUCTOR),
                                           *offset - seq_offset);

    if (rc == 0) {
        DEBUGMSGTL(("ksm", "Building ksm security parameters failed.\n"));
        retval = SNMPERR_TOO_LONG;
        goto error;
    }

    rc = asn_realloc_rbuild_header(wholeMsg, parms->wholeMsgLen,
                                         parms->wholeMsgOffset, 1,
                                         (u_char) (ASN_UNIVERSAL |
                                                   ASN_PRIMITIVE |
                                                   ASN_OCTET_STR),
                                         *offset - seq_offset);

    if (rc == 0) {
        DEBUGMSGTL(("ksm", "Building ksm security parameters failed.\n"));
        retval = SNMPERR_TOO_LONG;
        goto error;
    }

    DEBUGMSGTL(("ksm", "KSM: Security parameter encoding completed\n"));

    /*
     * We're done with the KSM security parameters - now we do the global
     * header and wrap up the whole PDU.
     */

    if (*parms->wholeMsgLen < parms->globalDataLen) {
        DEBUGMSGTL(("ksm", "Building global data failed.\n"));
        retval = SNMPERR_TOO_LONG;
        goto error;
    }

    *offset += parms->globalDataLen;
    memcpy(*wholeMsg + *parms->wholeMsgLen - *offset,
	   parms->globalData, parms->globalDataLen);

    rc = asn_realloc_rbuild_sequence(wholeMsg, parms->wholeMsgLen,
                                           offset, 1,
                                           (u_char) (ASN_SEQUENCE |
                                                     ASN_CONSTRUCTOR),
                                           *offset);

    if (rc == 0) {
        DEBUGMSGTL(("ksm", "Building master packet sequence.\n"));
        retval = SNMPERR_TOO_LONG;
        goto error;
    }

    DEBUGMSGTL(("ksm", "KSM: PDU master packet encoding complete.\n"));

    /*
     * Now we need to checksum the entire PDU (since it's built).
     */

#ifndef OLD_HEIMDAL /* since heimdal allocs the mem for us */
    CHECKSUM_CONTENTS(&pdu_checksum) = malloc(CHECKSUM_LENGTH(&pdu_checksum));

    if (!CHECKSUM_CONTENTS(&pdu_checksum)) {
        DEBUGMSGTL(("ksm", "Unable to malloc %d bytes for checksum\n",
                    CHECKSUM_LENGTH(&pdu_checksum)));
        retval = SNMPERR_MALLOC;
        goto error;
    }
#endif					/* ! OLD_HEIMDAL */
#ifdef NETSNMP_USE_KERBEROS_MIT

    input.data = (char *) (*wholeMsg + *parms->wholeMsgLen - *offset);
    input.length = *offset;
        retcode = krb5_c_make_checksum(kcontext, cksumtype, subkey,
                                       KSM_KEY_USAGE_CHECKSUM, &input,
                                       &pdu_checksum);

#elif defined(OLD_HEIMDAL)	/* NETSNMP_USE_KERBEROS_MIT */

	retcode = krb5_create_checksum(kcontext, heim_crypto,
				       KSM_KEY_USAGE_CHECKSUM, cksumtype,
				       *wholeMsg + *parms->wholeMsgLen
				       - *offset, *offset, &pdu_checksum);
#else                           /* NETSNMP_USE_KERBEROS_MIT */

    retcode = krb5_calculate_checksum(kcontext, cksumtype, *wholeMsg +
				      *parms->wholeMsgLen - *offset,
                                      *offset,
                                      (krb5_pointer) subkey->contents,
                                      subkey->length, &pdu_checksum);

#endif                          /* NETSNMP_USE_KERBEROS_MIT */

    if (retcode) {
        DEBUGMSGTL(("ksm", "Calculate checksum failed: %s\n",
                    error_message(retcode)));
        retval = SNMPERR_KRB5;
        snmp_set_detail(error_message(retcode));
        goto error;
    }

    DEBUGMSGTL(("ksm", "KSM: Checksum calculation complete.\n"));

    memcpy(cksum_pointer, CHECKSUM_CONTENTS(&pdu_checksum), CHECKSUM_LENGTH(&pdu_checksum));

    DEBUGMSGTL(("ksm", "KSM: Writing checksum of %d bytes at offset %d\n",
                (int)CHECKSUM_LENGTH(&pdu_checksum),
		(int)(cksum_pointer - (*wholeMsg + 1))));

    DEBUGMSGTL(("ksm", "KSM: Checksum:"));

    for (i = 0; i < CHECKSUM_LENGTH(&pdu_checksum); i++)
        DEBUGMSG(("ksm", " %02x",
                  (unsigned int) ((unsigned char *)CHECKSUM_CONTENTS(&pdu_checksum))[i]));

    DEBUGMSG(("ksm", "\n"));

    /*
     * If we're _not_ called as part of a response (null ksm_state),
     * then save the auth_context for later using our cache routines.
     */

    if (!ksm_state) {
        if ((retval = ksm_insert_cache(parms->pdu->msgid, auth_context,
                                       (u_char *) parms->secName,
                                       parms->secNameLen)) !=
            SNMPERR_SUCCESS)
            goto error;
        auth_context = NULL;
    }

    DEBUGMSGTL(("ksm", "KSM processing complete!\n"));

  error:

    if (CHECKSUM_CONTENTS(&pdu_checksum))
#ifdef NETSNMP_USE_KERBEROS_MIT
        krb5_free_checksum_contents(kcontext, &pdu_checksum);
#else                           /* NETSNMP_USE_KERBEROS_MIT */
        free(CHECKSUM_CONTENTS(&pdu_checksum));
#endif                          /* NETSNMP_USE_KERBEROS_MIT */

    if (ivector.data)
        free(ivector.data);

    if (subkey)
        krb5_free_keyblock(kcontext, subkey);

#ifdef OLD_HEIMDAL /* OLD_HEIMDAL */
    if (heim_crypto)
	    krb5_crypto_destroy(kcontext, heim_crypto);
#endif /* OLD_HEIMDAL */

    if (encrypted_data)
        free(encrypted_data);

    if (cc)
        krb5_cc_close(kcontext, cc);

    if (auth_context && !ksm_state)
        krb5_auth_con_free(kcontext, auth_context);

    return retval;
}

/****************************************************************************
 *
 * ksm_process_in_msg
 *
 * Parameters:
 *	(See list below...)
 *
 * Returns:
 *	KSM_ERR_NO_ERROR                        On success.
 *	SNMPERR_KRB5
 *	KSM_ERR_GENERIC_ERROR
 *	KSM_ERR_UNSUPPORTED_SECURITY_LEVEL
 *
 *
 * Processes an incoming message.
 *
 ****************************************************************************/

int
ksm_process_in_msg(struct snmp_secmod_incoming_params *parms)
{
    long            temp;
    krb5_cksumtype  cksumtype;
    krb5_auth_context auth_context = NULL;
    krb5_error_code retcode;
    krb5_checksum   checksum;
    krb5_data       ap_req, ivector;
    krb5_flags      flags;
    krb5_keyblock  *subkey = NULL;
#ifdef NETSNMP_USE_KERBEROS_MIT
    krb5_data       input, output;
    krb5_boolean    valid;
    krb5_enc_data   in_crypt;
#elif defined OLD_HEIMDAL	/* NETSNMP_USE_KERBEROS_MIT */
    krb5_data output;
    krb5_crypto heim_crypto = NULL;
#else                           /* NETSNMP_USE_KERBEROS_MIT */
    krb5_encrypt_block eblock;
#endif                          /* NETSNMP_USE_KERBEROS_MIT */
    krb5_ticket    *ticket = NULL;
    int             retval = SNMPERR_SUCCESS, response = 0;
    size_t          length =
        parms->wholeMsgLen - (u_int) (parms->secParams - parms->wholeMsg);
    u_char         *current = parms->secParams, type;
    size_t          cksumlength, blocksize;
    long            hint;
    char           *cname;
    struct ksm_secStateRef *ksm_state;
    struct ksm_cache_entry *entry;

    DEBUGMSGTL(("ksm", "Processing has begun\n"));

    CHECKSUM_CONTENTS(&checksum) = NULL;
    ap_req.data = NULL;
    ivector.length = 0;
    ivector.data = NULL;

    /*
     * First, parse the security parameters (because we need the subkey inside
     * of the ticket to do anything
     */

    if ((current = asn_parse_sequence(current, &length, &type,
                                      (ASN_UNIVERSAL | ASN_PRIMITIVE |
                                       ASN_OCTET_STR),
                                      "ksm first octet")) == NULL) {
        DEBUGMSGTL(("ksm", "Initial security paramter parsing failed\n"));

        retval = SNMPERR_ASN_PARSE_ERR;
        goto error;
    }

    if ((current = asn_parse_sequence(current, &length, &type,
                                      (ASN_SEQUENCE | ASN_CONSTRUCTOR),
                                      "ksm sequence")) == NULL) {
        DEBUGMSGTL(("ksm",
                    "Security parameter sequence parsing failed\n"));

        retval = SNMPERR_ASN_PARSE_ERR;
        goto error;
    }

    if ((current = asn_parse_int(current, &length, &type, &temp,
                                 sizeof(temp))) == NULL) {
        DEBUGMSGTL(("ksm", "Security parameter checksum type parsing"
                    "failed\n"));

        retval = SNMPERR_ASN_PARSE_ERR;
        goto error;
    }

    cksumtype = temp;

#ifdef NETSNMP_USE_KERBEROS_MIT
    if (!krb5_c_valid_cksumtype(cksumtype)) {
        DEBUGMSGTL(("ksm", "Invalid checksum type (%d)\n", cksumtype));

        retval = SNMPERR_KRB5;
        snmp_set_detail("Invalid checksum type");
        goto error;
    }

    if (!krb5_c_is_keyed_cksum(cksumtype)) {
        DEBUGMSGTL(("ksm", "Checksum type %d is not a keyed checksum\n",
                    cksumtype));
        snmp_set_detail("Checksum is not a keyed checksum");
        retval = SNMPERR_KRB5;
        goto error;
    }

    if (!krb5_c_is_coll_proof_cksum(cksumtype)) {
        DEBUGMSGTL(("ksm", "Checksum type %d is not a collision-proof "
                    "checksum\n", cksumtype));
        snmp_set_detail("Checksum is not a collision-proof checksum");
        retval = SNMPERR_KRB5;
        goto error;
    }
#else /* ! NETSNMP_USE_KERBEROS_MIT */
#ifdef OLD_HEIMDAL
    /* kludge */
    if (krb5_checksumsize(kcontext, cksumtype, &cksumlength)) {
#else					/* OLD_HEIMDAL */
    if (!valid_cksumtype(cksumtype)) {
#endif					/* OLD_HEIMDAL */
        DEBUGMSGTL(("ksm", "Invalid checksum type (%d)\n", cksumtype));

        retval = SNMPERR_KRB5;
        snmp_set_detail("Invalid checksum type");
        goto error;
    }

#ifdef OLD_HEIMDAL
    if (!krb5_checksum_is_keyed(kcontext, cksumtype)) {
#else					/* OLD_HEIMDAL */
    if (!is_keyed_cksum(cksumtype)) {
#endif					/* OLD_HEIMDAL */
        DEBUGMSGTL(("ksm", "Checksum type %d is not a keyed checksum\n",
                    cksumtype));
        snmp_set_detail("Checksum is not a keyed checksum");
        retval = SNMPERR_KRB5;
        goto error;
    }

#ifdef OLD_HEIMDAL
    if (!krb5_checksum_is_collision_proof(kcontext, cksumtype)) {
#else					/* OLD_HEIMDAL */
    if (!is_coll_proof_cksum(cksumtype)) {
#endif					/* OLD_HEIMDAL */
        DEBUGMSGTL(("ksm", "Checksum type %d is not a collision-proof "
                    "checksum\n", cksumtype));
        snmp_set_detail("Checksum is not a collision-proof checksum");
        retval = SNMPERR_KRB5;
        goto error;
    }
#endif /* NETSNMP_USE_KERBEROS_MIT */

    CHECKSUM_TYPE(&checksum) = cksumtype;

    cksumlength = length;

    if ((current = asn_parse_sequence(current, &cksumlength, &type,
                                      (ASN_UNIVERSAL | ASN_PRIMITIVE |
                                       ASN_OCTET_STR), "ksm checksum")) ==
        NULL) {
        DEBUGMSGTL(("ksm",
                    "Security parameter checksum parsing failed\n"));

        retval = SNMPERR_ASN_PARSE_ERR;
        goto error;
    }

    CHECKSUM_CONTENTS(&checksum) = malloc(cksumlength);
    if (!CHECKSUM_CONTENTS(&checksum)) {
        DEBUGMSGTL(("ksm", "Unable to malloc %d bytes for checksum.\n",
                    (int)cksumlength));
        retval = SNMPERR_MALLOC;
        goto error;
    }

    memcpy(CHECKSUM_CONTENTS(&checksum), current, cksumlength);

    CHECKSUM_LENGTH(&checksum) = cksumlength;
    CHECKSUM_TYPE(&checksum) = cksumtype;

    /*
     * Zero out the checksum so the validation works correctly
     */

    memset(current, 0, cksumlength);

    current += cksumlength;
    length = parms->wholeMsgLen - (u_int) (current - parms->wholeMsg);

    if ((current = asn_parse_sequence(current, &length, &type,
                                      (ASN_UNIVERSAL | ASN_PRIMITIVE |
                                       ASN_OCTET_STR), "ksm ap_req")) ==
        NULL) {
        DEBUGMSGTL(("ksm", "KSM security parameter AP_REQ/REP parsing "
                    "failed\n"));

        retval = SNMPERR_ASN_PARSE_ERR;
        goto error;
    }

    ap_req.length = length;
    ap_req.data = malloc(length);
    if (!ap_req.data) {
        DEBUGMSGTL(("ksm",
                    "KSM unable to malloc %d bytes for AP_REQ/REP.\n",
                    (int)length));
        retval = SNMPERR_MALLOC;
        goto error;
    }

    memcpy(ap_req.data, current, length);

    current += length;
    length = parms->wholeMsgLen - (u_int) (current - parms->wholeMsg);

    if ((current = asn_parse_int(current, &length, &type, &hint,
                                 sizeof(hint))) == NULL) {
        DEBUGMSGTL(("ksm",
                    "KSM security parameter hint parsing failed\n"));

        retval = SNMPERR_ASN_PARSE_ERR;
        goto error;
    }

    /*
     * Okay!  We've got it all!  Now try decoding the damn ticket.
     *
     * But of course there's a WRINKLE!  We need to figure out if we're
     * processing a AP_REQ or an AP_REP.  How do we do that?  We're going
     * to cheat, and look at the first couple of bytes (which is what
     * the Kerberos library routines do anyway).
     *
     * If there are ever new Kerberos message formats, we'll need to fix
     * this here.
     *
     * If it's a _response_, then we need to get the auth_context
     * from our cache.
     */

    if (ap_req.length
#ifndef NETSNMP_USE_KERBEROS_HEIMDAL
        && (ap_req.data[0] == 0x6e || ap_req.data[0] == 0x4e)) {
#else				/* NETSNMP_USE_KERBEROS_HEIMDAL */
        && (((char *)ap_req.data)[0] == 0x6e || ((char *)ap_req.data)[0] == 0x4e)) {
#endif

        /*
         * We need to initalize the authorization context, and set the
         * replay cache in it (and initialize the replay cache if we
         * haven't already
         */

        retcode = krb5_auth_con_init(kcontext, &auth_context);

        if (retcode) {
            DEBUGMSGTL(("ksm", "krb5_auth_con_init failed: %s\n",
                        error_message(retcode)));
            retval = SNMPERR_KRB5;
            snmp_set_detail(error_message(retcode));
            goto error;
        }

        if (!rcache) {
            krb5_data       server;
            server.data = service_host;
            server.length = strlen(server.data);

            retcode = krb5_get_server_rcache(kcontext, &server, &rcache);

            if (retcode) {
                DEBUGMSGTL(("ksm", "krb5_get_server_rcache failed: %s\n",
                            error_message(retcode)));
                retval = SNMPERR_KRB5;
                snmp_set_detail(error_message(retcode));
                goto error;
            }
        }

        retcode = krb5_auth_con_setrcache(kcontext, auth_context, rcache);

        if (retcode) {
            DEBUGMSGTL(("ksm", "krb5_auth_con_setrcache failed: %s\n",
                        error_message(retcode)));
            retval = SNMPERR_KRB5;
            snmp_set_detail(error_message(retcode));
            goto error;
        }

        retcode = krb5_rd_req(kcontext, &auth_context, &ap_req, NULL,
                              keytab, &flags, &ticket);

        krb5_auth_con_setrcache(kcontext, auth_context, NULL);

        if (retcode) {
            DEBUGMSGTL(("ksm", "krb5_rd_req() failed: %s\n",
                        error_message(retcode)));
            retval = SNMPERR_KRB5;
            snmp_set_detail(error_message(retcode));
            goto error;
        }

        retcode =
            krb5_unparse_name(kcontext, TICKET_CLIENT(ticket), &cname);

        if (retcode == 0) {
            DEBUGMSGTL(("ksm", "KSM authenticated principal name: %s\n",
                        cname));
            free(cname);
        }

        /*
         * Check to make sure AP_OPTS_MUTUAL_REQUIRED was set
         */

        if (!(flags & AP_OPTS_MUTUAL_REQUIRED)) {
            DEBUGMSGTL(("ksm",
                        "KSM MUTUAL_REQUIRED not set in request!\n"));
            retval = SNMPERR_KRB5;
            snmp_set_detail("MUTUAL_REQUIRED not set in message");
            goto error;
        }

        retcode =
            krb5_auth_con_getremotesubkey(kcontext, auth_context, &subkey);

        if (retcode) {
            DEBUGMSGTL(("ksm", "KSM remote subkey retrieval failed: %s\n",
                        error_message(retcode)));
            retval = SNMPERR_KRB5;
            snmp_set_detail(error_message(retcode));
            goto error;
        }

#ifndef NETSNMP_USE_KERBEROS_HEIMDAL
    } else if (ap_req.length && (ap_req.data[0] == 0x6f ||
                                 ap_req.data[0] == 0x4f)) {
#else				/* NETSNMP_USE_KERBEROS_HEIMDAL */
    } else if (ap_req.length && (((char *)ap_req.data)[0] == 0x6f ||
                                 ((char *)ap_req.data)[0] == 0x4f)) {
#endif				/* NETSNMP_USE_KERBEROS_HEIMDAL */
        /*
         * Looks like a response; let's see if we've got that auth_context
         * in our cache.
         */

        krb5_ap_rep_enc_part *repl = NULL;

        response = 1;

        entry = ksm_get_cache(parms->pdu->msgid);

        if (!entry) {
            DEBUGMSGTL(("ksm",
                        "KSM: Unable to find auth_context for PDU with "
                        "message ID of %ld\n", parms->pdu->msgid));
            retval = SNMPERR_KRB5;
            goto error;
        }

        auth_context = entry->auth_context;

        /*
         * In that case, let's call the rd_rep function
         */

        retcode = krb5_rd_rep(kcontext, auth_context, &ap_req, &repl);

        if (repl)
            krb5_free_ap_rep_enc_part(kcontext, repl);

        if (retcode) {
            DEBUGMSGTL(("ksm", "KSM: krb5_rd_rep() failed: %s\n",
                        error_message(retcode)));
            retval = SNMPERR_KRB5;
            goto error;
        }

        DEBUGMSGTL(("ksm", "KSM: krb5_rd_rep() decoded successfully.\n"));

        retcode =
            krb5_auth_con_getlocalsubkey(kcontext, auth_context, &subkey);

        if (retcode) {
            DEBUGMSGTL(("ksm", "Unable to retrieve local subkey: %s\n",
                        error_message(retcode)));
            retval = SNMPERR_KRB5;
            snmp_set_detail("Unable to retrieve local subkey");
            goto error;
        }

    } else {
#ifndef NETSNMP_USE_KERBEROS_HEIMDAL
        DEBUGMSGTL(("ksm", "Unknown Kerberos message type (%02x)\n",
                    ap_req.data[0]));
#else 				/* NETSNMP_USE_KERBEROS_HEIMDAL */
	 DEBUGMSGTL(("ksm", "Unknown Kerberos message type (%02x)\n",
                    ((char *)ap_req.data)[0]));
#endif
        retval = SNMPERR_KRB5;
        snmp_set_detail("Unknown Kerberos message type");
        goto error;
    }

#ifdef NETSNMP_USE_KERBEROS_MIT
    input.data = (char *) parms->wholeMsg;
    input.length = parms->wholeMsgLen;

    retcode =
        krb5_c_verify_checksum(kcontext, subkey, KSM_KEY_USAGE_CHECKSUM,
                               &input, &checksum, &valid);
#elif defined(OLD_HEIMDAL)	/* NETSNMP_USE_KERBEROS_MIT */
    retcode = krb5_crypto_init(kcontext, subkey, 0, &heim_crypto);
    if (retcode) {
            DEBUGMSGTL(("ksm", "krb5_crypto_init failed: %s\n",
                        error_message(retcode)));
            snmp_set_detail(error_message(retcode));
            retval = SNMPERR_KRB5;
            goto error;
    }
    retcode = krb5_verify_checksum(kcontext, heim_crypto,
				   KSM_KEY_USAGE_CHECKSUM, parms->wholeMsg,
				   parms->wholeMsgLen, &checksum);
#else                           /* NETSNMP_USE_KERBEROS_MIT */
    retcode = krb5_verify_checksum(kcontext, cksumtype, &checksum,
                                   parms->wholeMsg, parms->wholeMsgLen,
                                   (krb5_pointer) subkey->contents,
                                   subkey->length);
#endif                          /* NETSNMP_USE_KERBEROS_MIT */

    if (retcode) {
        DEBUGMSGTL(("ksm", "KSM checksum verification failed: %s\n",
                    error_message(retcode)));
        retval = SNMPERR_KRB5;
        snmp_set_detail(error_message(retcode));
        goto error;
    }

    /*
     * Don't ask me why they didn't simply return an error, but we have
     * to check to see if "valid" is false.
     */

#ifdef NETSNMP_USE_KERBEROS_MIT
    if (!valid) {
        DEBUGMSGTL(("ksm", "Computed checksum did not match supplied "
                    "checksum!\n"));
        retval = SNMPERR_KRB5;
        snmp_set_detail
            ("Computed checksum did not match supplied checksum");
        goto error;
    }
#endif                          /* NETSNMP_USE_KERBEROS_MIT */

    /*
     * Handle an encrypted PDU.  Note that it's an OCTET_STRING of the
     * output of whatever Kerberos cryptosystem you're using (defined by
     * the encryption type).  Note that this is NOT the EncryptedData
     * sequence - it's what goes in the "cipher" field of EncryptedData.
     */

    if (parms->secLevel == SNMP_SEC_LEVEL_AUTHPRIV) {

        if ((current = asn_parse_sequence(current, &length, &type,
                                          (ASN_UNIVERSAL | ASN_PRIMITIVE |
                                           ASN_OCTET_STR), "ksm pdu")) ==
            NULL) {
            DEBUGMSGTL(("ksm", "KSM sPDU octet decoding failed\n"));
            retval = SNMPERR_ASN_PARSE_ERR;
            goto error;
        }

        /*
         * The PDU is now pointed at by "current", and the length is in
         * "length".
         */

        DEBUGMSGTL(("ksm", "KSM starting sPDU decode\n"));

        /*
         * We need to set up a blank initialization vector for the decryption.
         * Use a block of all zero's (which is dependent on the block size
         * of the encryption method).
         */

#ifdef NETSNMP_USE_KERBEROS_MIT

        retcode = krb5_c_block_size(kcontext, subkey->enctype, &blocksize);

        if (retcode) {
            DEBUGMSGTL(("ksm",
                        "Unable to determine crypto block size: %s\n",
                        error_message(retcode)));
            snmp_set_detail(error_message(retcode));
            retval = SNMPERR_KRB5;
            goto error;
        }
#elif defined(OLD_HEIMDAL)	/* NETSNMP_USE_KERBEROS_MIT */
#else                           /* NETSNMP_USE_KERBEROS_MIT */

        blocksize =
            krb5_enctype_array[subkey->enctype]->system->block_length;

#endif                          /* NETSNMP_USE_KERBEROS_MIT */

#ifndef OLD_HEIMDAL
        ivector.data = malloc(blocksize);

        if (!ivector.data) {
            DEBUGMSGTL(("ksm", "Unable to allocate %d bytes for ivector\n",
                        (int)blocksize));
            retval = SNMPERR_MALLOC;
            goto error;
        }

        ivector.length = blocksize;
        memset(ivector.data, 0, blocksize);

#ifndef NETSNMP_USE_KERBEROS_MIT

        krb5_use_enctype(kcontext, &eblock, subkey->enctype);

        retcode = krb5_process_key(kcontext, &eblock, subkey);

        if (retcode) {
            DEBUGMSGTL(("ksm", "KSM key post-processing failed: %s\n",
                        error_message(retcode)));
            snmp_set_detail(error_message(retcode));
            retval = SNMPERR_KRB5;
            goto error;
        }
#endif                          /* !NETSNMP_USE_KERBEROS_MIT */

#endif /* ! OLD_HEIMDAL */

        if (length > *parms->scopedPduLen) {
            DEBUGMSGTL(("ksm", "KSM not enough room - have %d bytes to "
                        "decrypt but only %d bytes available\n", (int)length,
                        (int)*parms->scopedPduLen));
            retval = SNMPERR_TOO_LONG;
#ifndef NETSNMP_USE_KERBEROS_MIT
#ifndef OLD_HEIMDAL
            krb5_finish_key(kcontext, &eblock);
#endif                          /* ! OLD_HEIMDAL */
#endif                          /* ! NETSNMP_USE_KERBEROS_MIT */
            goto error;
        }
#ifdef NETSNMP_USE_KERBEROS_MIT
        in_crypt.ciphertext.data = (char *) current;
        in_crypt.ciphertext.length = length;
        in_crypt.enctype = subkey->enctype;
        output.data = (char *) *parms->scopedPdu;
        output.length = *parms->scopedPduLen;

        retcode =
            krb5_c_decrypt(kcontext, subkey, KSM_KEY_USAGE_ENCRYPTION,
                           &ivector, &in_crypt, &output);
#elif defined (OLD_HEIMDAL)	/* NETSNMP_USE_KERBEROS_MIT */
	retcode = krb5_decrypt(kcontext, heim_crypto, KSM_KEY_USAGE_ENCRYPTION,
			       current, length, &output);
	if (retcode == 0) {
		*parms->scopedPdu = (char *) output.data;
		*parms->scopedPduLen = output.length;
		krb5_data_zero(&output);
	}
#else                           /* NETSNMP_USE_KERBEROS_MIT */

        retcode = krb5_decrypt(kcontext, (krb5_pointer) current,
                               *parms->scopedPdu, length, &eblock,
                               ivector.data);

        krb5_finish_key(kcontext, &eblock);

#endif                          /* NETSNMP_USE_KERBEROS_MIT */

        if (retcode) {
            DEBUGMSGTL(("ksm", "Decryption failed: %s\n",
                        error_message(retcode)));
            snmp_set_detail(error_message(retcode));
            retval = SNMPERR_KRB5;
            goto error;
        }

        *parms->scopedPduLen = length;

    } else {
        /*
         * Clear PDU
         */

        *parms->scopedPdu = current;
        *parms->scopedPduLen =
            parms->wholeMsgLen - (current - parms->wholeMsg);
    }

    /*
     * A HUGE GROSS HACK
     */

    *parms->maxSizeResponse = parms->maxMsgSize - 200;

    DEBUGMSGTL(("ksm", "KSM processing complete\n"));

    /*
     * Set the secName to the right value (a hack for now).  But that's
     * only used for when we're processing a request, not a response.
     */

    if (!response) {

        retcode = krb5_unparse_name(kcontext, TICKET_CLIENT(ticket),
                                    &cname);

        if (retcode) {
            DEBUGMSGTL(("ksm", "KSM krb5_unparse_name failed: %s\n",
                        error_message(retcode)));
            snmp_set_detail(error_message(retcode));
            retval = SNMPERR_KRB5;
            goto error;
        }

        if (strlen(cname) > *parms->secNameLen + 1) {
            DEBUGMSGTL(("ksm",
                        "KSM: Principal length (%d) is too long (%d)\n",
                        (int)strlen(cname), (int)*parms->secNameLen));
            retval = SNMPERR_TOO_LONG;
            free(cname);
            goto error;
        }

        strcpy(parms->secName, cname);
        *parms->secNameLen = strlen(cname);

        free(cname);

        /*
         * Also, if we're not a response, keep around our auth_context so we
         * can encode the reply message correctly
         */

        ksm_state = SNMP_MALLOC_STRUCT(ksm_secStateRef);

        if (!ksm_state) {
            DEBUGMSGTL(("ksm", "KSM unable to malloc memory for "
                        "ksm_secStateRef\n"));
            retval = SNMPERR_MALLOC;
            goto error;
        }

        ksm_state->auth_context = auth_context;
        auth_context = NULL;
        ksm_state->cksumtype = cksumtype;

        *parms->secStateRef = ksm_state;
    } else {

        /*
         * We _still_ have to set the secName in process_in_msg().  Do
         * that now with what we were passed in before (we cached it,
         * remember?)
         */

        memcpy(parms->secName, entry->secName, entry->secNameLen);
        *parms->secNameLen = entry->secNameLen;
    }

    /*
     * Just in case
     */

    parms->secEngineID = null_id;
    *parms->secEngineIDLen = 0;

    auth_context = NULL;        /* So we don't try to free it on success */

  error:
    if (retval == SNMPERR_ASN_PARSE_ERR &&
        snmp_increment_statistic(STAT_SNMPINASNPARSEERRS) == 0)
        DEBUGMSGTL(("ksm", "Failed to increment statistics.\n"));

    if (subkey)
        krb5_free_keyblock(kcontext, subkey);

#ifdef OLD_HEIMDAL /* OLD_HEIMDAL */
    if (heim_crypto)
	    krb5_crypto_destroy(kcontext, heim_crypto);
#endif /* OLD_HEIMDAL */

    if (CHECKSUM_CONTENTS(&checksum))
        free(CHECKSUM_CONTENTS(&checksum));

    if (ivector.data)
        free(ivector.data);

    if (ticket)
        krb5_free_ticket(kcontext, ticket);

    if (!response && auth_context)
        krb5_auth_con_free(kcontext, auth_context);

    if (ap_req.data)
        free(ap_req.data);

    return retval;
}
