/*
 * agent_index.c
 *
 * Maintain a registry of index allocations
 *      (Primarily required for AgentX support,
 *       but it could be more widely useable).
 */


#include <net-snmp/net-snmp-config.h>
#include <signal.h>
#if HAVE_STRING_H
#include <string.h>
#endif
#if HAVE_STDLIB_H
#include <stdlib.h>
#endif
#include <sys/types.h>
#include <stdio.h>
#include <fcntl.h>
#if HAVE_WINSOCK_H
#include <winsock.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_NETINET_IN_H
#include <netinet/in.h>
#endif

#include <net-snmp/net-snmp-includes.h>
#include <net-snmp/agent/net-snmp-agent-includes.h>
#include <net-snmp/agent/agent_callbacks.h>
#include <net-snmp/agent/agent_index.h>

#include "snmpd.h"
#include "mibgroup/struct.h"
#include <net-snmp/agent/table.h>
#include <net-snmp/agent/table_iterator.h>

#ifdef USING_AGENTX_SUBAGENT_MODULE
#include "agentx/subagent.h"
#include "agentx/client.h"
#endif

        /*
         * Initial support for index allocation
         */

struct snmp_index {
    netsnmp_variable_list *varbind;     /* or pointer to var_list ? */
    int             allocated;
    netsnmp_session *session;
    struct snmp_index *next_oid;
    struct snmp_index *prev_oid;
    struct snmp_index *next_idx;
}              *snmp_index_head = NULL;

extern netsnmp_session *main_session;

/*
 * The caller is responsible for free()ing the memory returned by
 * this function.  
 */

char           *
register_string_index(oid * name, size_t name_len, char *cp)
{
    netsnmp_variable_list varbind, *res;

    memset(&varbind, 0, sizeof(netsnmp_variable_list));
    varbind.type = ASN_OCTET_STR;
    snmp_set_var_objid(&varbind, name, name_len);
    if (cp != ANY_STRING_INDEX) {
        snmp_set_var_value(&varbind, (u_char *) cp, strlen(cp));
        res = register_index(&varbind, ALLOCATE_THIS_INDEX, main_session);
    } else {
        res = register_index(&varbind, ALLOCATE_ANY_INDEX, main_session);
    }

    if (res == NULL) {
        return NULL;
    } else {
        char           *rv = strdup(res->val.string);
        free(res);
        return rv;
    }
}

int
register_int_index(oid * name, size_t name_len, int val)
{
    netsnmp_variable_list varbind, *res;

    memset(&varbind, 0, sizeof(netsnmp_variable_list));
    varbind.type = ASN_INTEGER;
    snmp_set_var_objid(&varbind, name, name_len);
    varbind.val.string = varbind.buf;
    if (val != ANY_INTEGER_INDEX) {
        varbind.val_len = sizeof(long);
        *varbind.val.integer = val;
        res = register_index(&varbind, ALLOCATE_THIS_INDEX, main_session);
    } else {
        res = register_index(&varbind, ALLOCATE_ANY_INDEX, main_session);
    }

    if (res == NULL) {
        return -1;
    } else {
        int             rv = *(res->val.integer);
        free(res);
        return rv;
    }
}

/*
 * The caller is responsible for free()ing the memory returned by
 * this function.  
 */

netsnmp_variable_list *
register_oid_index(oid * name, size_t name_len,
                   oid * value, size_t value_len)
{
    netsnmp_variable_list varbind;

    memset(&varbind, 0, sizeof(netsnmp_variable_list));
    varbind.type = ASN_OBJECT_ID;
    snmp_set_var_objid(&varbind, name, name_len);
    if (value != ANY_OID_INDEX) {
        snmp_set_var_value(&varbind, (u_char *) value,
                           value_len * sizeof(oid));
        return register_index(&varbind, ALLOCATE_THIS_INDEX, main_session);
    } else {
        return register_index(&varbind, ALLOCATE_ANY_INDEX, main_session);
    }
}

/*
 * The caller is responsible for free()ing the memory returned by
 * this function.  
 */

netsnmp_variable_list *
register_index(netsnmp_variable_list * varbind, int flags,
               netsnmp_session * ss)
{
    netsnmp_variable_list *rv = NULL;
    struct snmp_index *new_index, *idxptr, *idxptr2;
    struct snmp_index *prev_oid_ptr, *prev_idx_ptr;
    int             res, res2, i;

    DEBUGMSGTL(("register_index", "register "));
    DEBUGMSGVAR(("register_index", varbind));
    DEBUGMSG(("register_index", "for session %08p\n", ss));

#if defined(USING_AGENTX_SUBAGENT_MODULE) && !defined(TESTING)
    if (netsnmp_ds_get_boolean(NETSNMP_DS_APPLICATION_ID, 
			       NETSNMP_DS_AGENT_ROLE) == SUB_AGENT) {
        return (agentx_register_index(ss, varbind, flags));
    }
#endif
    /*
     * Look for the requested OID entry 
     */
    prev_oid_ptr = NULL;
    prev_idx_ptr = NULL;
    res = 1;
    res2 = 1;
    for (idxptr = snmp_index_head; idxptr != NULL;
         prev_oid_ptr = idxptr, idxptr = idxptr->next_oid) {
        if ((res = snmp_oid_compare(varbind->name, varbind->name_length,
                                    idxptr->varbind->name,
                                    idxptr->varbind->name_length)) <= 0)
            break;
    }

    /*
     * Found the OID - now look at the registered indices 
     */
    if (res == 0 && idxptr) {
        if (varbind->type != idxptr->varbind->type)
            return NULL;        /* wrong type */

        /*
         * If we've been asked for an arbitrary new value,
         *      then find the end of the list.
         * If we've been asked for any arbitrary value,
         *      then look for an unused entry, and use that.
         *      If there aren't any, continue as for new.
         * Otherwise, locate the given value in the (sorted)
         *      list of already allocated values
         */
        if (flags & ALLOCATE_ANY_INDEX) {
            for (idxptr2 = idxptr; idxptr2 != NULL;
                 prev_idx_ptr = idxptr2, idxptr2 = idxptr2->next_idx) {

                if (flags == ALLOCATE_ANY_INDEX && !(idxptr2->allocated)) {
                    if ((rv =
                         snmp_clone_varbind(idxptr2->varbind)) != NULL) {
                        idxptr2->session = ss;
                        idxptr2->allocated = 1;
                    }
                    return rv;
                }
            }
        } else {
            for (idxptr2 = idxptr; idxptr2 != NULL;
                 prev_idx_ptr = idxptr2, idxptr2 = idxptr2->next_idx) {
                switch (varbind->type) {
                case ASN_INTEGER:
                    res2 =
                        (*varbind->val.integer -
                         *idxptr2->varbind->val.integer);
                    break;
                case ASN_OCTET_STR:
                    i = SNMP_MIN(varbind->val_len,
                                 idxptr2->varbind->val_len);
                    res2 =
                        memcmp(varbind->val.string,
                               idxptr2->varbind->val.string, i);
                    break;
                case ASN_OBJECT_ID:
                    res2 =
                        snmp_oid_compare(varbind->val.objid,
                                         varbind->val_len / sizeof(oid),
                                         idxptr2->varbind->val.objid,
                                         idxptr2->varbind->val_len /
                                         sizeof(oid));
                    break;
                default:
                    return NULL;        /* wrong type */
                }
                if (res2 <= 0)
                    break;
            }
            if (res2 == 0) {
                if (idxptr2->allocated) {
                    /*
                     * No good: the index is in use.  
                     */
                    return NULL;
                } else {
                    /*
                     * Okay, it's unallocated, we can just claim ownership
                     * here.  
                     */
                    if ((rv =
                         snmp_clone_varbind(idxptr2->varbind)) != NULL) {
                        idxptr2->session = ss;
                        idxptr2->allocated = 1;
                    }
                    return rv;
                }
            }
        }
    }

    /*
     * OK - we've now located where the new entry needs to
     *      be fitted into the index registry tree          
     * To recap:
     *      'prev_oid_ptr' points to the head of the OID index
     *          list prior to this one.  If this is null, then
     *          it means that this is the first OID in the list.
     *      'idxptr' points either to the head of this OID list,
     *          or the next OID (if this is a new OID request)
     *          These can be distinguished by the value of 'res'.
     *
     *      'prev_idx_ptr' points to the index entry that sorts
     *          immediately prior to the requested value (if any).
     *          If an arbitrary value is required, then this will
     *          point to the last allocated index.
     *          If this pointer is null, then either this is a new
     *          OID request, or the requested value is the first
     *          in the list.
     *      'idxptr2' points to the next sorted index (if any)
     *          but is not actually needed any more.
     *
     *  Clear?  Good!
     *      I hope you've been paying attention.
     *          There'll be a test later :-)
     */

    /*
     *      We proceed by creating the new entry
     *         (by copying the entry provided)
     */
    new_index = (struct snmp_index *) calloc(1, sizeof(struct snmp_index));
    if (new_index == NULL)
        return NULL;

    if (0 == snmp_varlist_add_variable(&new_index->varbind,
                                       varbind->name,
                                       varbind->name_length,
                                       varbind->type,
                                       varbind->val.string,
                                       varbind->val_len)) {
        /*
         * if (snmp_clone_var( varbind, new_index->varbind ) != 0 ) 
         */
        free(new_index);
        return NULL;
    }
    new_index->session = ss;
    new_index->allocated = 1;

    if (varbind->type == ASN_OCTET_STR && flags == ALLOCATE_THIS_INDEX)
        new_index->varbind->val.string[new_index->varbind->val_len] = 0;

    /*
     * If we've been given a value, then we can use that, but
     *    otherwise, we need to create a new value for this entry.
     * Note that ANY_INDEX and NEW_INDEX are both covered by this
     *   test (since NEW_INDEX & ANY_INDEX = ANY_INDEX, remember?)
     */
    if (flags & ALLOCATE_ANY_INDEX) {
        if (prev_idx_ptr) {
            if (snmp_clone_var(prev_idx_ptr->varbind, new_index->varbind)
                != 0) {
                free(new_index);
                return NULL;
            }
        } else
            new_index->varbind->val.string = new_index->varbind->buf;

        switch (varbind->type) {
        case ASN_INTEGER:
            if (prev_idx_ptr) {
                (*new_index->varbind->val.integer)++;
            } else
                *(new_index->varbind->val.integer) = 1;
            new_index->varbind->val_len = sizeof(long);
            break;
        case ASN_OCTET_STR:
            if (prev_idx_ptr) {
                i = new_index->varbind->val_len - 1;
                while (new_index->varbind->buf[i] == 'z') {
                    new_index->varbind->buf[i] = 'a';
                    i--;
                    if (i < 0) {
                        i = new_index->varbind->val_len;
                        new_index->varbind->buf[i] = 'a';
                        new_index->varbind->buf[i + 1] = 0;
                    }
                }
                new_index->varbind->buf[i]++;
            } else
                strcpy((char *) new_index->varbind->buf, "aaaa");
            new_index->varbind->val_len =
                strlen((char *) new_index->varbind->buf);
            break;
        case ASN_OBJECT_ID:
            if (prev_idx_ptr) {
                i = prev_idx_ptr->varbind->val_len / sizeof(oid) - 1;
                while (new_index->varbind->val.objid[i] == 255) {
                    new_index->varbind->val.objid[i] = 1;
                    i--;
                    if (i == 0 && new_index->varbind->val.objid[0] == 2) {
                        new_index->varbind->val.objid[0] = 1;
                        i = new_index->varbind->val_len / sizeof(oid);
                        new_index->varbind->val.objid[i] = 0;
                        new_index->varbind->val_len += sizeof(oid);
                    }
                }
                new_index->varbind->val.objid[i]++;
            } else {
                /*
                 * If the requested OID name is small enough,
                 * *   append another OID (1) and use this as the
                 * *   default starting value for new indexes.
                 */
                if ((varbind->name_length + 1) * sizeof(oid) <= 40) {
                    for (i = 0; i < (int) varbind->name_length; i++)
                        new_index->varbind->val.objid[i] =
                            varbind->name[i];
                    new_index->varbind->val.objid[varbind->name_length] =
                        1;
                    new_index->varbind->val_len =
                        (varbind->name_length + 1) * sizeof(oid);
                } else {
                    /*
                     * Otherwise use '.1.1.1.1...' 
                     */
                    i = 40 / sizeof(oid);
                    if (i > 4)
                        i = 4;
                    new_index->varbind->val_len = i * (sizeof(oid));
                    for (i--; i >= 0; i--)
                        new_index->varbind->val.objid[i] = 1;
                }
            }
            break;
        default:
            snmp_free_var(new_index->varbind);
            free(new_index);
            return NULL;        /* Index type not supported */
        }
    }

    /*
     * Try to duplicate the new varbind for return.  
     */

    if ((rv = snmp_clone_varbind(new_index->varbind)) == NULL) {
        snmp_free_var(new_index->varbind);
        free(new_index);
        return NULL;
    }

    /*
     * Right - we've set up the new entry.
     * All that remains is to link it into the tree.
     * There are a number of possible cases here,
     *   so watch carefully.
     */
    if (prev_idx_ptr) {
        new_index->next_idx = prev_idx_ptr->next_idx;
        new_index->next_oid = prev_idx_ptr->next_oid;
        prev_idx_ptr->next_idx = new_index;
    } else {
        if (res == 0 && idxptr) {
            new_index->next_idx = idxptr;
            new_index->next_oid = idxptr->next_oid;
        } else {
            new_index->next_idx = NULL;
            new_index->next_oid = idxptr;
        }

        if (prev_oid_ptr) {
            while (prev_oid_ptr) {
                prev_oid_ptr->next_oid = new_index;
                prev_oid_ptr = prev_oid_ptr->next_idx;
            }
        } else
            snmp_index_head = new_index;
    }
    return rv;
}

        /*
         * Release an allocated index,
         *   to allow it to be used elsewhere
         */
int
release_index(netsnmp_variable_list * varbind)
{
    return (unregister_index(varbind, TRUE, NULL));
}

        /*
         * Completely remove an allocated index,
         *   due to errors in the registration process.
         */
int
remove_index(netsnmp_variable_list * varbind, netsnmp_session * ss)
{
    return (unregister_index(varbind, FALSE, ss));
}

void
unregister_index_by_session(netsnmp_session * ss)
{
    struct snmp_index *idxptr, *idxptr2;
    for (idxptr = snmp_index_head; idxptr != NULL;
         idxptr = idxptr->next_oid)
        for (idxptr2 = idxptr; idxptr2 != NULL;
             idxptr2 = idxptr2->next_idx)
            if (idxptr2->session == ss) {
                idxptr2->allocated = 0;
                idxptr2->session = NULL;
            }
}


int
unregister_index(netsnmp_variable_list * varbind, int remember,
                 netsnmp_session * ss)
{
    struct snmp_index *idxptr, *idxptr2;
    struct snmp_index *prev_oid_ptr, *prev_idx_ptr;
    int             res, res2, i;

#if defined(USING_AGENTX_SUBAGENT_MODULE) && !defined(TESTING)
    if (netsnmp_ds_get_boolean(NETSNMP_DS_APPLICATION_ID, 
			       NETSNMP_DS_AGENT_ROLE) == SUB_AGENT) {
        return (agentx_unregister_index(ss, varbind));
    }
#endif
    /*
     * Look for the requested OID entry 
     */
    prev_oid_ptr = NULL;
    prev_idx_ptr = NULL;
    res = 1;
    res2 = 1;
    for (idxptr = snmp_index_head; idxptr != NULL;
         prev_oid_ptr = idxptr, idxptr = idxptr->next_oid) {
        if ((res = snmp_oid_compare(varbind->name, varbind->name_length,
                                    idxptr->varbind->name,
                                    idxptr->varbind->name_length)) <= 0)
            break;
    }

    if (res != 0)
        return INDEX_ERR_NOT_ALLOCATED;
    if (varbind->type != idxptr->varbind->type)
        return INDEX_ERR_WRONG_TYPE;

    for (idxptr2 = idxptr; idxptr2 != NULL;
         prev_idx_ptr = idxptr2, idxptr2 = idxptr2->next_idx) {
        switch (varbind->type) {
        case ASN_INTEGER:
            res2 =
                (*varbind->val.integer -
                 *idxptr2->varbind->val.integer);
            break;
        case ASN_OCTET_STR:
            i = SNMP_MIN(varbind->val_len,
                         idxptr2->varbind->val_len);
            res2 =
                memcmp(varbind->val.string,
                       idxptr2->varbind->val.string, i);
            break;
        case ASN_OBJECT_ID:
            res2 =
                snmp_oid_compare(varbind->val.objid,
                                 varbind->val_len / sizeof(oid),
                                 idxptr2->varbind->val.objid,
                                 idxptr2->varbind->val_len /
                                 sizeof(oid));
            break;
        default:
            return INDEX_ERR_WRONG_TYPE;        /* wrong type */
        }
        if (res2 <= 0)
            break;
    }
    if (res2 != 0 || (res2 == 0 && !idxptr2->allocated)) {
        return INDEX_ERR_NOT_ALLOCATED;
    }
    if (ss != idxptr2->session)
        return INDEX_ERR_WRONG_SESSION;

    /*
     *  If this is a "normal" index unregistration,
     *      mark the index entry as unused, but leave
     *      it in situ.  This allows differentiation
     *      between ANY_INDEX and NEW_INDEX
     */
    if (remember) {
        idxptr2->allocated = 0; /* Unused index */
        idxptr2->session = NULL;
        return SNMP_ERR_NOERROR;
    }
    /*
     *  If this is a failed attempt to register a
     *      number of indexes, the successful ones
     *      must be removed completely.
     */
    if (prev_idx_ptr) {
        prev_idx_ptr->next_idx = idxptr2->next_idx;
    } else if (prev_oid_ptr) {
        if (idxptr2->next_idx)  /* Use p_idx_ptr as a temp variable */
            prev_idx_ptr = idxptr2->next_idx;
        else
            prev_idx_ptr = idxptr2->next_oid;
        while (prev_oid_ptr) {
            prev_oid_ptr->next_oid = prev_idx_ptr;
            prev_oid_ptr = prev_oid_ptr->next_idx;
        }
    } else {
        if (idxptr2->next_idx)
            snmp_index_head = idxptr2->next_idx;
        else
            snmp_index_head = idxptr2->next_oid;
    }
    snmp_free_var(idxptr2->varbind);
    free(idxptr2);
    return SNMP_ERR_NOERROR;
}

int
unregister_string_index(oid * name, size_t name_len, char *cp)
{
    netsnmp_variable_list varbind;

    memset(&varbind, 0, sizeof(netsnmp_variable_list));
    varbind.type = ASN_OCTET_STR;
    snmp_set_var_objid(&varbind, name, name_len);
    snmp_set_var_value(&varbind, (u_char *) cp, strlen(cp));
    return (unregister_index(&varbind, FALSE, main_session));
}

int
unregister_int_index(oid * name, size_t name_len, int val)
{
    netsnmp_variable_list varbind;

    memset(&varbind, 0, sizeof(netsnmp_variable_list));
    varbind.type = ASN_INTEGER;
    snmp_set_var_objid(&varbind, name, name_len);
    varbind.val.string = varbind.buf;
    varbind.val_len = sizeof(long);
    *varbind.val.integer = val;
    return (unregister_index(&varbind, FALSE, main_session));
}

int
unregister_oid_index(oid * name, size_t name_len,
                     oid * value, size_t value_len)
{
    netsnmp_variable_list varbind;

    memset(&varbind, 0, sizeof(netsnmp_variable_list));
    varbind.type = ASN_OBJECT_ID;
    snmp_set_var_objid(&varbind, name, name_len);
    snmp_set_var_value(&varbind, (u_char *) value,
                       value_len * sizeof(oid));
    return (unregister_index(&varbind, FALSE, main_session));
}

void
dump_idx_registry(void)
{
    struct snmp_index *idxptr, *idxptr2;
    u_char         *sbuf = NULL, *ebuf = NULL;
    size_t          sbuf_len = 0, sout_len = 0, ebuf_len = 0, eout_len = 0;

    if (snmp_index_head != NULL) {
        printf("\nIndex Allocations:\n");
    }

    for (idxptr = snmp_index_head; idxptr != NULL;
         idxptr = idxptr->next_oid) {
        sout_len = 0;
        if (sprint_realloc_objid(&sbuf, &sbuf_len, &sout_len, 1,
                                 idxptr->varbind->name,
                                 idxptr->varbind->name_length)) {
            printf("%s indexes:\n", sbuf);
        } else {
            printf("%s [TRUNCATED] indexes:\n", sbuf);
        }

        for (idxptr2 = idxptr; idxptr2 != NULL;
             idxptr2 = idxptr2->next_idx) {
            switch (idxptr2->varbind->type) {
            case ASN_INTEGER:
                printf("    %ld for session %8p, allocated %d\n",
                       *idxptr2->varbind->val.integer, idxptr2->session,
                       idxptr2->allocated);
                break;
            case ASN_OCTET_STR:
                printf("    \"%s\" for session %8p, allocated %d\n",
                       idxptr2->varbind->val.string, idxptr2->session,
                       idxptr2->allocated);
                break;
            case ASN_OBJECT_ID:
                eout_len = 0;
                if (sprint_realloc_objid(&ebuf, &ebuf_len, &eout_len, 1,
                                         idxptr2->varbind->val.objid,
                                         idxptr2->varbind->val_len /
                                         sizeof(oid))) {
                    printf("    %s for session %8p, allocated %d\n", ebuf,
                           idxptr2->session, idxptr2->allocated);
                } else {
                    printf
                        ("    %s [TRUNCATED] for sess %8p, allocated %d\n",
                         ebuf, idxptr2->session, idxptr2->allocated);
                }
                break;
            default:
                printf("unsupported type (%d/0x%02x)\n",
                       idxptr2->varbind->type, idxptr2->varbind->type);
            }
        }
    }

    if (sbuf != NULL) {
        free(sbuf);
    }
    if (ebuf != NULL) {
        free(ebuf);
    }
}

unsigned long
count_indexes(oid * name, size_t namelen, int include_unallocated)
{
    struct snmp_index *i = NULL, *j = NULL;
    unsigned long   n = 0;

    for (i = snmp_index_head; i != NULL; i = i->next_oid) {
        if (netsnmp_oid_equals(name, namelen,
                             i->varbind->name,
                             i->varbind->name_length) == 0) {
            for (j = i; j != NULL; j = j->next_idx) {
                if (j->allocated || include_unallocated) {
                    n++;
                }
            }
        }
    }
    return n;
}


#ifdef TESTING
netsnmp_variable_list varbind;
netsnmp_session main_sess, *main_session = &main_sess;

void
test_string_register(int n, char *cp)
{
    varbind->name[4] = n;
    if (register_string_index(varbind->name, varbind.name_length, cp) ==
        NULL)
        printf("allocating %s failed\n", cp);
}

void
test_int_register(int n, int val)
{
    varbind->name[4] = n;
    if (register_int_index(varbind->name, varbind.name_length, val) == -1)
        printf("allocating %d/%d failed\n", n, val);
}

void
test_oid_register(int n, int subid)
{
    netsnmp_variable_list *res;

    varbind->name[4] = n;
    if (subid != -1) {
        varbind->val.objid[5] = subid;
        res = register_oid_index(varbind->name, varbind.name_length,
                                 varbind->val.objid,
                                 varbind->val_len / sizeof(oid));
    } else
        res =
            register_oid_index(varbind->name, varbind.name_length, NULL,
                               0);

    if (res == NULL)
        printf("allocating %d/%d failed\n", n, subid);
}

void
main(int argc, char argv[])
{
    oid             name[] = { 1, 2, 3, 4, 0 };
    int             i;

    memset(&varbind, 0, sizeof(netsnmp_variable_list));
    snmp_set_var_objid(&varbind, name, 5);
    varbind->type = ASN_OCTET_STR;
    /*
     * Test index structure linking:
     *      a) sorted by OID
     */
    test_string_register(20, "empty OID");
    test_string_register(10, "first OID");
    test_string_register(40, "last OID");
    test_string_register(30, "middle OID");

    /*
     *      b) sorted by index value
     */
    test_string_register(25, "eee: empty IDX");
    test_string_register(25, "aaa: first IDX");
    test_string_register(25, "zzz: last IDX");
    test_string_register(25, "mmm: middle IDX");
    printf("This next one should fail....\n");
    test_string_register(25, "eee: empty IDX"); /* duplicate */
    printf("done\n");

    /*
     *      c) test initial index linking
     */
    test_string_register(5, "eee: empty initial IDX");
    test_string_register(5, "aaa: replace initial IDX");

    /*
     *      Did it all work?
     */
    dump_idx_registry();
    unregister_index_by_session(main_session);
    /*
     *  Now test index allocation
     *      a) integer values
     */
    test_int_register(110, -1); /* empty */
    test_int_register(110, -1); /* append */
    test_int_register(110, 10); /* append exact */
    printf("This next one should fail....\n");
    test_int_register(110, 10); /* exact duplicate */
    printf("done\n");
    test_int_register(110, -1); /* append */
    test_int_register(110, 5);  /* insert exact */

    /*
     *      b) string values
     */
    test_string_register(120, NULL);    /* empty */
    test_string_register(120, NULL);    /* append */
    test_string_register(120, "aaaz");
    test_string_register(120, NULL);    /* minor rollover */
    test_string_register(120, "zzzz");
    test_string_register(120, NULL);    /* major rollover */

    /*
     *      c) OID values
     */

    test_oid_register(130, -1); /* empty */
    test_oid_register(130, -1); /* append */

    varbind->val_len = varbind.name_length * sizeof(oid);
    memcpy(varbind->buf, varbind.name, varbind.val_len);
    varbind->val.objid = (oid *) varbind.buf;
    varbind->val_len += sizeof(oid);

    test_oid_register(130, 255);        /* append exact */
    test_oid_register(130, -1); /* minor rollover */
    test_oid_register(130, 100);        /* insert exact */
    printf("This next one should fail....\n");
    test_oid_register(130, 100);        /* exact duplicate */
    printf("done\n");

    varbind->val.objid = (oid *) varbind.buf;
    for (i = 0; i < 6; i++)
        varbind->val.objid[i] = 255;
    varbind->val.objid[0] = 1;
    test_oid_register(130, 255);        /* set up rollover  */
    test_oid_register(130, -1); /* medium rollover */

    for (i = 0; i < 6; i++)
        varbind->val.objid[i] = 255;
    varbind->val.objid[0] = 2;
    test_oid_register(130, 255);        /* set up rollover  */
    test_oid_register(130, -1); /* major rollover */

    /*
     *      Did it all work?
     */
    dump_idx_registry();

    /*
     *      Test the various "invalid" requests
     *      (unsupported types, mis-matched types, etc)
     */
    printf("The rest of these should fail....\n");
    test_oid_register(110, -1);
    test_oid_register(110, 100);
    test_oid_register(120, -1);
    test_oid_register(120, 100);
    test_string_register(110, NULL);
    test_string_register(110, "aaaa");
    test_string_register(130, NULL);
    test_string_register(130, "aaaa");
    test_int_register(120, -1);
    test_int_register(120, 1);
    test_int_register(130, -1);
    test_int_register(130, 1);
    printf("done - this dump should be the same as before\n");
    dump_idx_registry();
}
#endif
