/*
 * Note: this file originally auto-generated by mib2c using
 *       version : 1.67 $ of : mfd-interface.m2c,v $ 
 *
 * $Id$
 */
/*
 * *********************************************************************
 * *********************************************************************
 * *********************************************************************
 * ***                                                               ***
 * ***  NOTE NOTE NOTE NOTE NOTE NOTE NOTE NOTE NOTE NOTE NOTE NOTE  ***
 * ***                                                               ***
 * ***                                                               ***
 * ***       THIS FILE DOES NOT CONTAIN ANY USER EDITABLE CODE.      ***
 * ***                                                               ***
 * ***                                                               ***
 * ***       THE GENERATED CODE IS INTERNAL IMPLEMENTATION, AND      ***
 * ***                                                               ***
 * ***                                                               ***
 * ***    IS SUBJECT TO CHANGE WITHOUT WARNING IN FUTURE RELEASES.   ***
 * ***                                                               ***
 * ***                                                               ***
 * *********************************************************************
 * *********************************************************************
 * *********************************************************************
 */

/*
 * standard Net-SNMP includes 
 */
#include <net-snmp/net-snmp-config.h>
#include <net-snmp/net-snmp-includes.h>
#include <net-snmp/agent/net-snmp-agent-includes.h>

/*
 * include our parent header 
 */
#include "tcpConnectionTable.h"


#include <net-snmp/agent/table_container.h>
#include <net-snmp/library/container.h>

#include "tcpConnectionTable_interface.h"

#include <ctype.h>

/**********************************************************************
 **********************************************************************
 ***
 *** Table tcpConnectionTable
 ***
 **********************************************************************
 **********************************************************************/
/*
 * TCP-MIB::tcpConnectionTable is subid 19 of tcp.
 * Its status is Current.
 * OID: .1.3.6.1.2.1.6.19, length: 8
 */
typedef struct tcpConnectionTable_interface_ctx_s {

    netsnmp_container *container;
    netsnmp_cache  *cache;

    tcpConnectionTable_registration *user_ctx;

    netsnmp_table_registration_info tbl_info;

    netsnmp_baby_steps_access_methods access_multiplexer;

    u_int           table_dirty;

} tcpConnectionTable_interface_ctx;

static tcpConnectionTable_interface_ctx tcpConnectionTable_if_ctx;

static void
                _tcpConnectionTable_container_init(tcpConnectionTable_interface_ctx *
                                                   if_ctx);
static void
                _tcpConnectionTable_container_shutdown(tcpConnectionTable_interface_ctx *
                                                       if_ctx);


netsnmp_container *
tcpConnectionTable_container_get(void)
{
    return tcpConnectionTable_if_ctx.container;
}

tcpConnectionTable_registration *
tcpConnectionTable_registration_get(void)
{
    return tcpConnectionTable_if_ctx.user_ctx;
}

tcpConnectionTable_registration *
tcpConnectionTable_registration_set(tcpConnectionTable_registration *
                                    newreg)
{
    tcpConnectionTable_registration *old =
        tcpConnectionTable_if_ctx.user_ctx;
    tcpConnectionTable_if_ctx.user_ctx = newreg;
    return old;
}

int
tcpConnectionTable_container_size(void)
{
    return CONTAINER_SIZE(tcpConnectionTable_if_ctx.container);
}

u_int
tcpConnectionTable_dirty_get(void)
{
    return tcpConnectionTable_if_ctx.table_dirty;
}

void
tcpConnectionTable_dirty_set(u_int status)
{
    DEBUGMSGTL(("tcpConnectionTable:tcpConnectionTable_dirty_set",
                "called. was %d, now %d\n",
                tcpConnectionTable_if_ctx.table_dirty, status));
    tcpConnectionTable_if_ctx.table_dirty = status;
}

/*
 * mfd multiplexer modes
 */
static Netsnmp_Node_Handler _mfd_tcpConnectionTable_pre_request;
static Netsnmp_Node_Handler _mfd_tcpConnectionTable_post_request;
static Netsnmp_Node_Handler _mfd_tcpConnectionTable_object_lookup;
static Netsnmp_Node_Handler _mfd_tcpConnectionTable_get_values;
#ifndef NETSNMP_DISABLE_SET_SUPPORT
static Netsnmp_Node_Handler _mfd_tcpConnectionTable_check_objects;
static Netsnmp_Node_Handler _mfd_tcpConnectionTable_undo_setup;
static Netsnmp_Node_Handler _mfd_tcpConnectionTable_set_values;
static Netsnmp_Node_Handler _mfd_tcpConnectionTable_undo_cleanup;
static Netsnmp_Node_Handler _mfd_tcpConnectionTable_undo_values;
static Netsnmp_Node_Handler _mfd_tcpConnectionTable_commit;
static Netsnmp_Node_Handler _mfd_tcpConnectionTable_undo_commit;
static Netsnmp_Node_Handler _mfd_tcpConnectionTable_irreversible_commit;
static Netsnmp_Node_Handler _mfd_tcpConnectionTable_check_dependencies;

NETSNMP_STATIC_INLINE int
                _tcpConnectionTable_undo_column(tcpConnectionTable_rowreq_ctx * rowreq_ctx,
                                                netsnmp_variable_list *
                                                var, int column);
#endif

/**
 * @internal
 * Initialize the table tcpConnectionTable 
 *    (Define its contents and how it's structured)
 */
void
_tcpConnectionTable_initialize_interface(tcpConnectionTable_registration *
                                         reg_ptr, u_long flags)
{
    netsnmp_baby_steps_access_methods *access_multiplexer =
        &tcpConnectionTable_if_ctx.access_multiplexer;
    netsnmp_table_registration_info *tbl_info =
        &tcpConnectionTable_if_ctx.tbl_info;
    netsnmp_handler_registration *reginfo;
    netsnmp_mib_handler *handler;
    int             mfd_modes = 0;

    DEBUGMSGTL(("internal:tcpConnectionTable:_tcpConnectionTable_initialize_interface", "called\n"));


    /*************************************************
     *
     * save interface context for tcpConnectionTable
     */
    /*
     * Setting up the table's definition
     */
    netsnmp_table_helper_add_indexes(tbl_info, ASN_INTEGER,
                                               /** index: tcpConnectionLocalAddressType */
                                     ASN_OCTET_STR,
                                                 /** index: tcpConnectionLocalAddress */
                                     ASN_UNSIGNED,
                                                /** index: tcpConnectionLocalPort */
                                     ASN_INTEGER,
                                               /** index: tcpConnectionRemAddressType */
                                     ASN_OCTET_STR,
                                                 /** index: tcpConnectionRemAddress */
                                     ASN_UNSIGNED,
                                                /** index: tcpConnectionRemPort */
                                     0);

    /*
     * Define the minimum and maximum accessible columns.  This
     * optimizes retrieval. 
     */
    tbl_info->min_column = TCPCONNECTIONTABLE_MIN_COL;
    tbl_info->max_column = TCPCONNECTIONTABLE_MAX_COL;

    /*
     * save users context
     */
    tcpConnectionTable_if_ctx.user_ctx = reg_ptr;

    /*
     * call data access initialization code
     */
    tcpConnectionTable_init_data(reg_ptr);

    /*
     * set up the container
     */
    _tcpConnectionTable_container_init(&tcpConnectionTable_if_ctx);
    if (NULL == tcpConnectionTable_if_ctx.container) {
        snmp_log(LOG_ERR,
                 "could not initialize container for tcpConnectionTable\n");
        return;
    }

    /*
     * access_multiplexer: REQUIRED wrapper for get request handling
     */
    access_multiplexer->object_lookup =
        _mfd_tcpConnectionTable_object_lookup;
    access_multiplexer->get_values = _mfd_tcpConnectionTable_get_values;

    /*
     * no wrappers yet
     */
    access_multiplexer->pre_request = _mfd_tcpConnectionTable_pre_request;
    access_multiplexer->post_request =
        _mfd_tcpConnectionTable_post_request;


#ifndef NETSNMP_DISABLE_SET_SUPPORT
    /*
     * REQUIRED wrappers for set request handling
     */
    access_multiplexer->object_syntax_checks =
        _mfd_tcpConnectionTable_check_objects;
    access_multiplexer->undo_setup = _mfd_tcpConnectionTable_undo_setup;
    access_multiplexer->undo_cleanup =
        _mfd_tcpConnectionTable_undo_cleanup;
    access_multiplexer->set_values = _mfd_tcpConnectionTable_set_values;
    access_multiplexer->undo_sets = _mfd_tcpConnectionTable_undo_values;

    /*
     * no wrappers yet
     */
    access_multiplexer->commit = _mfd_tcpConnectionTable_commit;
    access_multiplexer->undo_commit = _mfd_tcpConnectionTable_undo_commit;
    access_multiplexer->irreversible_commit =
        _mfd_tcpConnectionTable_irreversible_commit;

    /*
     * REQUIRED for tables with dependencies
     */
    access_multiplexer->consistency_checks =
        _mfd_tcpConnectionTable_check_dependencies;
#endif

    /*************************************************
     *
     * Create a registration, save our reg data, register table.
     */
    DEBUGMSGTL(("tcpConnectionTable:init_tcpConnectionTable",
                "Registering tcpConnectionTable as a mibs-for-dummies table.\n"));
    handler =
        netsnmp_baby_steps_access_multiplexer_get(access_multiplexer);
    reginfo =
        netsnmp_handler_registration_create("tcpConnectionTable", handler,
                                            tcpConnectionTable_oid,
                                            tcpConnectionTable_oid_size,
                                            HANDLER_CAN_BABY_STEP
#ifndef NETSNMP_DISABLE_SET_SUPPORT
                                          | HANDLER_CAN_RWRITE
#endif
                                          );
    if (NULL == reginfo) {
        snmp_log(LOG_ERR, "error registering table tcpConnectionTable\n");
        return;
    }
    reginfo->my_reg_void = &tcpConnectionTable_if_ctx;

    /*************************************************
     *
     * set up baby steps handler, create it and inject it
     */
    if (access_multiplexer->object_lookup)
        mfd_modes |= BABY_STEP_OBJECT_LOOKUP;
    if (access_multiplexer->pre_request)
        mfd_modes |= BABY_STEP_PRE_REQUEST;
    if (access_multiplexer->post_request)
        mfd_modes |= BABY_STEP_POST_REQUEST;

#ifndef NETSNMP_DISABLE_SET_SUPPORT
    if (access_multiplexer->set_values)
        mfd_modes |= BABY_STEP_SET_VALUES;
    if (access_multiplexer->irreversible_commit)
        mfd_modes |= BABY_STEP_IRREVERSIBLE_COMMIT;
    if (access_multiplexer->object_syntax_checks)
        mfd_modes |= BABY_STEP_CHECK_OBJECT;

    if (access_multiplexer->undo_setup)
        mfd_modes |= BABY_STEP_UNDO_SETUP;
    if (access_multiplexer->undo_cleanup)
        mfd_modes |= BABY_STEP_UNDO_CLEANUP;
    if (access_multiplexer->undo_sets)
        mfd_modes |= BABY_STEP_UNDO_SETS;

    if (access_multiplexer->row_creation)
        mfd_modes |= BABY_STEP_ROW_CREATE;
    if (access_multiplexer->consistency_checks)
        mfd_modes |= BABY_STEP_CHECK_CONSISTENCY;
    if (access_multiplexer->commit)
        mfd_modes |= BABY_STEP_COMMIT;
    if (access_multiplexer->undo_commit)
        mfd_modes |= BABY_STEP_UNDO_COMMIT;
#endif

    handler = netsnmp_baby_steps_handler_get(mfd_modes);
    netsnmp_inject_handler(reginfo, handler);

    /*************************************************
     *
     * inject row_merge helper with prefix rootoid_len + 2 (entry.col)
     */
    handler = netsnmp_get_row_merge_handler(reginfo->rootoid_len + 2);
    netsnmp_inject_handler(reginfo, handler);

    /*************************************************
     *
     * inject container_table helper
     */
    handler =
        netsnmp_container_table_handler_get(tbl_info,
                                            tcpConnectionTable_if_ctx.
                                            container,
                                            TABLE_CONTAINER_KEY_NETSNMP_INDEX);
    netsnmp_inject_handler(reginfo, handler);

    /*************************************************
     *
     * inject cache helper
     */
    if (NULL != tcpConnectionTable_if_ctx.cache) {
        handler =
            netsnmp_cache_handler_get(tcpConnectionTable_if_ctx.cache);
        netsnmp_inject_handler(reginfo, handler);
    }

    /*
     * register table
     */
    netsnmp_register_table(reginfo, tbl_info);

}                               /* _tcpConnectionTable_initialize_interface */

/**
 * @internal
 * Shutdown the table tcpConnectionTable
 */
void
_tcpConnectionTable_shutdown_interface(tcpConnectionTable_registration *
                                       reg_ptr)
{
    /*
     * shutdown the container
     */
    _tcpConnectionTable_container_shutdown(&tcpConnectionTable_if_ctx);
}

void
tcpConnectionTable_valid_columns_set(netsnmp_column_info *vc)
{
    tcpConnectionTable_if_ctx.tbl_info.valid_columns = vc;
}                               /* tcpConnectionTable_valid_columns_set */

/**
 * @internal
 * convert the index component stored in the context to an oid
 */
int
tcpConnectionTable_index_to_oid(netsnmp_index * oid_idx,
                                tcpConnectionTable_mib_index * mib_idx)
{
    int             err = SNMP_ERR_NOERROR;

    /*
     * temp storage for parsing indexes
     */
    /*
     * tcpConnectionLocalAddressType(1)/InetAddressType/ASN_INTEGER/long(u_long)//l/a/w/E/r/d/h
     */
    netsnmp_variable_list var_tcpConnectionLocalAddressType;
    /*
     * tcpConnectionLocalAddress(2)/InetAddress/ASN_OCTET_STR/char(char)//L/a/w/e/R/d/h
     */
    netsnmp_variable_list var_tcpConnectionLocalAddress;
    /*
     * tcpConnectionLocalPort(3)/InetPortNumber/ASN_UNSIGNED/u_long(u_long)//l/a/w/e/R/d/H
     */
    netsnmp_variable_list var_tcpConnectionLocalPort;
    /*
     * tcpConnectionRemAddressType(4)/InetAddressType/ASN_INTEGER/long(u_long)//l/a/w/E/r/d/h
     */
    netsnmp_variable_list var_tcpConnectionRemAddressType;
    /*
     * tcpConnectionRemAddress(5)/InetAddress/ASN_OCTET_STR/char(char)//L/a/w/e/R/d/h
     */
    netsnmp_variable_list var_tcpConnectionRemAddress;
    /*
     * tcpConnectionRemPort(6)/InetPortNumber/ASN_UNSIGNED/u_long(u_long)//l/a/w/e/R/d/H
     */
    netsnmp_variable_list var_tcpConnectionRemPort;

    /*
     * set up varbinds
     */
    memset(&var_tcpConnectionLocalAddressType, 0x00,
           sizeof(var_tcpConnectionLocalAddressType));
    var_tcpConnectionLocalAddressType.type = ASN_INTEGER;
    memset(&var_tcpConnectionLocalAddress, 0x00,
           sizeof(var_tcpConnectionLocalAddress));
    var_tcpConnectionLocalAddress.type = ASN_OCTET_STR;
    memset(&var_tcpConnectionLocalPort, 0x00,
           sizeof(var_tcpConnectionLocalPort));
    var_tcpConnectionLocalPort.type = ASN_UNSIGNED;
    memset(&var_tcpConnectionRemAddressType, 0x00,
           sizeof(var_tcpConnectionRemAddressType));
    var_tcpConnectionRemAddressType.type = ASN_INTEGER;
    memset(&var_tcpConnectionRemAddress, 0x00,
           sizeof(var_tcpConnectionRemAddress));
    var_tcpConnectionRemAddress.type = ASN_OCTET_STR;
    memset(&var_tcpConnectionRemPort, 0x00,
           sizeof(var_tcpConnectionRemPort));
    var_tcpConnectionRemPort.type = ASN_UNSIGNED;

    /*
     * chain temp index varbinds together
     */
    var_tcpConnectionLocalAddressType.next_variable =
        &var_tcpConnectionLocalAddress;
    var_tcpConnectionLocalAddress.next_variable =
        &var_tcpConnectionLocalPort;
    var_tcpConnectionLocalPort.next_variable =
        &var_tcpConnectionRemAddressType;
    var_tcpConnectionRemAddressType.next_variable =
        &var_tcpConnectionRemAddress;
    var_tcpConnectionRemAddress.next_variable = &var_tcpConnectionRemPort;
    var_tcpConnectionRemPort.next_variable = NULL;


    DEBUGMSGTL(("verbose:tcpConnectionTable:tcpConnectionTable_index_to_oid", "called\n"));

    /*
     * tcpConnectionLocalAddressType(1)/InetAddressType/ASN_INTEGER/long(u_long)//l/a/w/E/r/d/h 
     */
    snmp_set_var_value(&var_tcpConnectionLocalAddressType,
                       (u_char *) & mib_idx->tcpConnectionLocalAddressType,
                       sizeof(mib_idx->tcpConnectionLocalAddressType));

    /*
     * tcpConnectionLocalAddress(2)/InetAddress/ASN_OCTET_STR/char(char)//L/a/w/e/R/d/h 
     */
    snmp_set_var_value(&var_tcpConnectionLocalAddress,
                       (u_char *) & mib_idx->tcpConnectionLocalAddress,
                       mib_idx->tcpConnectionLocalAddress_len *
                       sizeof(mib_idx->tcpConnectionLocalAddress[0]));

    /*
     * tcpConnectionLocalPort(3)/InetPortNumber/ASN_UNSIGNED/u_long(u_long)//l/a/w/e/R/d/H 
     */
    snmp_set_var_value(&var_tcpConnectionLocalPort,
                       (u_char *) & mib_idx->tcpConnectionLocalPort,
                       sizeof(mib_idx->tcpConnectionLocalPort));

    /*
     * tcpConnectionRemAddressType(4)/InetAddressType/ASN_INTEGER/long(u_long)//l/a/w/E/r/d/h 
     */
    snmp_set_var_value(&var_tcpConnectionRemAddressType,
                       (u_char *) & mib_idx->tcpConnectionRemAddressType,
                       sizeof(mib_idx->tcpConnectionRemAddressType));

    /*
     * tcpConnectionRemAddress(5)/InetAddress/ASN_OCTET_STR/char(char)//L/a/w/e/R/d/h 
     */
    snmp_set_var_value(&var_tcpConnectionRemAddress,
                       (u_char *) & mib_idx->tcpConnectionRemAddress,
                       mib_idx->tcpConnectionRemAddress_len *
                       sizeof(mib_idx->tcpConnectionRemAddress[0]));

    /*
     * tcpConnectionRemPort(6)/InetPortNumber/ASN_UNSIGNED/u_long(u_long)//l/a/w/e/R/d/H 
     */
    snmp_set_var_value(&var_tcpConnectionRemPort,
                       (u_char *) & mib_idx->tcpConnectionRemPort,
                       sizeof(mib_idx->tcpConnectionRemPort));


    err = build_oid_noalloc(oid_idx->oids, oid_idx->len, &oid_idx->len,
                            NULL, 0, &var_tcpConnectionLocalAddressType);
    if (err)
        snmp_log(LOG_ERR, "error %d converting index to oid\n", err);

    /*
     * parsing may have allocated memory. free it.
     */
    snmp_reset_var_buffers(&var_tcpConnectionLocalAddressType);

    return err;
}                               /* tcpConnectionTable_index_to_oid */

/**
 * extract tcpConnectionTable indexes from a netsnmp_index
 *
 * @retval SNMP_ERR_NOERROR  : no error
 * @retval SNMP_ERR_GENERR   : error
 */
int
tcpConnectionTable_index_from_oid(netsnmp_index * oid_idx,
                                  tcpConnectionTable_mib_index * mib_idx)
{
    int             err = SNMP_ERR_NOERROR;

    /*
     * temp storage for parsing indexes
     */
    /*
     * tcpConnectionLocalAddressType(1)/InetAddressType/ASN_INTEGER/long(u_long)//l/a/w/E/r/d/h
     */
    netsnmp_variable_list var_tcpConnectionLocalAddressType;
    /*
     * tcpConnectionLocalAddress(2)/InetAddress/ASN_OCTET_STR/char(char)//L/a/w/e/R/d/h
     */
    netsnmp_variable_list var_tcpConnectionLocalAddress;
    /*
     * tcpConnectionLocalPort(3)/InetPortNumber/ASN_UNSIGNED/u_long(u_long)//l/a/w/e/R/d/H
     */
    netsnmp_variable_list var_tcpConnectionLocalPort;
    /*
     * tcpConnectionRemAddressType(4)/InetAddressType/ASN_INTEGER/long(u_long)//l/a/w/E/r/d/h
     */
    netsnmp_variable_list var_tcpConnectionRemAddressType;
    /*
     * tcpConnectionRemAddress(5)/InetAddress/ASN_OCTET_STR/char(char)//L/a/w/e/R/d/h
     */
    netsnmp_variable_list var_tcpConnectionRemAddress;
    /*
     * tcpConnectionRemPort(6)/InetPortNumber/ASN_UNSIGNED/u_long(u_long)//l/a/w/e/R/d/H
     */
    netsnmp_variable_list var_tcpConnectionRemPort;

    /*
     * set up varbinds
     */
    memset(&var_tcpConnectionLocalAddressType, 0x00,
           sizeof(var_tcpConnectionLocalAddressType));
    var_tcpConnectionLocalAddressType.type = ASN_INTEGER;
    memset(&var_tcpConnectionLocalAddress, 0x00,
           sizeof(var_tcpConnectionLocalAddress));
    var_tcpConnectionLocalAddress.type = ASN_OCTET_STR;
    memset(&var_tcpConnectionLocalPort, 0x00,
           sizeof(var_tcpConnectionLocalPort));
    var_tcpConnectionLocalPort.type = ASN_UNSIGNED;
    memset(&var_tcpConnectionRemAddressType, 0x00,
           sizeof(var_tcpConnectionRemAddressType));
    var_tcpConnectionRemAddressType.type = ASN_INTEGER;
    memset(&var_tcpConnectionRemAddress, 0x00,
           sizeof(var_tcpConnectionRemAddress));
    var_tcpConnectionRemAddress.type = ASN_OCTET_STR;
    memset(&var_tcpConnectionRemPort, 0x00,
           sizeof(var_tcpConnectionRemPort));
    var_tcpConnectionRemPort.type = ASN_UNSIGNED;

    /*
     * chain temp index varbinds together
     */
    var_tcpConnectionLocalAddressType.next_variable =
        &var_tcpConnectionLocalAddress;
    var_tcpConnectionLocalAddress.next_variable =
        &var_tcpConnectionLocalPort;
    var_tcpConnectionLocalPort.next_variable =
        &var_tcpConnectionRemAddressType;
    var_tcpConnectionRemAddressType.next_variable =
        &var_tcpConnectionRemAddress;
    var_tcpConnectionRemAddress.next_variable = &var_tcpConnectionRemPort;
    var_tcpConnectionRemPort.next_variable = NULL;


    DEBUGMSGTL(("verbose:tcpConnectionTable:tcpConnectionTable_index_from_oid", "called\n"));

    /*
     * parse the oid into the individual index components
     */
    err = parse_oid_indexes(oid_idx->oids, oid_idx->len,
                            &var_tcpConnectionLocalAddressType);
    if (err == SNMP_ERR_NOERROR) {
        /*
         * copy out values
         */
        mib_idx->tcpConnectionLocalAddressType =
            *((u_long *) var_tcpConnectionLocalAddressType.val.string);
        /*
         * NOTE: val_len is in bytes, tcpConnectionLocalAddress_len might not be
         */
        if (var_tcpConnectionLocalAddress.val_len >
            sizeof(mib_idx->tcpConnectionLocalAddress))
            err = SNMP_ERR_GENERR;
        else {
            memcpy(mib_idx->tcpConnectionLocalAddress,
                   var_tcpConnectionLocalAddress.val.string,
                   var_tcpConnectionLocalAddress.val_len);
            mib_idx->tcpConnectionLocalAddress_len =
                var_tcpConnectionLocalAddress.val_len /
                sizeof(mib_idx->tcpConnectionLocalAddress[0]);
        }
        mib_idx->tcpConnectionLocalPort =
            *((u_long *) var_tcpConnectionLocalPort.val.string);
        mib_idx->tcpConnectionRemAddressType =
            *((u_long *) var_tcpConnectionRemAddressType.val.string);
        /*
         * NOTE: val_len is in bytes, tcpConnectionRemAddress_len might not be
         */
        if (var_tcpConnectionRemAddress.val_len >
            sizeof(mib_idx->tcpConnectionRemAddress))
            err = SNMP_ERR_GENERR;
        else {
            memcpy(mib_idx->tcpConnectionRemAddress,
                   var_tcpConnectionRemAddress.val.string,
                   var_tcpConnectionRemAddress.val_len);
            mib_idx->tcpConnectionRemAddress_len =
                var_tcpConnectionRemAddress.val_len /
                sizeof(mib_idx->tcpConnectionRemAddress[0]);
        }
        mib_idx->tcpConnectionRemPort =
            *((u_long *) var_tcpConnectionRemPort.val.string);


    }

    /*
     * parsing may have allocated memory. free it.
     */
    snmp_reset_var_buffers(&var_tcpConnectionLocalAddressType);

    return err;
}                               /* tcpConnectionTable_index_from_oid */


/*
 *********************************************************************
 * @internal
 * allocate resources for a tcpConnectionTable_rowreq_ctx
 */
tcpConnectionTable_rowreq_ctx *
tcpConnectionTable_allocate_rowreq_ctx(tcpConnectionTable_data * data,
                                       void *user_init_ctx)
{
    tcpConnectionTable_rowreq_ctx *rowreq_ctx =
        SNMP_MALLOC_TYPEDEF(tcpConnectionTable_rowreq_ctx);

    DEBUGMSGTL(("internal:tcpConnectionTable:tcpConnectionTable_allocate_rowreq_ctx", "called\n"));

    if (NULL == rowreq_ctx) {
        snmp_log(LOG_ERR, "Couldn't allocate memory for a "
                 "tcpConnectionTable_rowreq_ctx.\n");
        return NULL;
    } else {
        if (NULL != data) {
            /*
             * track if we got data from user
             */
            rowreq_ctx->rowreq_flags |= MFD_ROW_DATA_FROM_USER;
            rowreq_ctx->data = data;
        } else if (NULL ==
                   (rowreq_ctx->data =
                    tcpConnectionTable_allocate_data())) {
            SNMP_FREE(rowreq_ctx);
            return NULL;
        }
    }

    /*
     * undo context will be allocated when needed (in *_undo_setup)
     */

    rowreq_ctx->oid_idx.oids = rowreq_ctx->oid_tmp;

    rowreq_ctx->tcpConnectionTable_data_list = NULL;

    /*
     * if we allocated data, call init routine
     */
    if (!(rowreq_ctx->rowreq_flags & MFD_ROW_DATA_FROM_USER)) {
        if (SNMPERR_SUCCESS !=
            tcpConnectionTable_rowreq_ctx_init(rowreq_ctx,
                                               user_init_ctx)) {
            tcpConnectionTable_release_rowreq_ctx(rowreq_ctx);
            rowreq_ctx = NULL;
        }
    }

    return rowreq_ctx;
}                               /* tcpConnectionTable_allocate_rowreq_ctx */

/*
 * @internal
 * release resources for a tcpConnectionTable_rowreq_ctx
 */
void
tcpConnectionTable_release_rowreq_ctx(tcpConnectionTable_rowreq_ctx *
                                      rowreq_ctx)
{
    DEBUGMSGTL(("internal:tcpConnectionTable:tcpConnectionTable_release_rowreq_ctx", "called\n"));

    netsnmp_assert(NULL != rowreq_ctx);

    tcpConnectionTable_rowreq_ctx_cleanup(rowreq_ctx);

    /*
     * for non-transient data, don't free data we got from the user
     */
    if ((rowreq_ctx->data) &&
        !(rowreq_ctx->rowreq_flags & MFD_ROW_DATA_FROM_USER))
        tcpConnectionTable_release_data(rowreq_ctx->data);

    if (rowreq_ctx->undo)
        tcpConnectionTable_release_data(rowreq_ctx->undo);

    /*
     * free index oid pointer
     */
    if (rowreq_ctx->oid_idx.oids != rowreq_ctx->oid_tmp)
        free(rowreq_ctx->oid_idx.oids);

    SNMP_FREE(rowreq_ctx);
}                               /* tcpConnectionTable_release_rowreq_ctx */

/**
 * @internal
 * wrapper
 */
static int
_mfd_tcpConnectionTable_pre_request(netsnmp_mib_handler *handler,
                                    netsnmp_handler_registration *reginfo,
                                    netsnmp_agent_request_info
                                    *agtreq_info,
                                    netsnmp_request_info *requests)
{
    int             rc;

    DEBUGMSGTL(("internal:tcpConnectionTable:_mfd_tcpConnectionTable_pre_request", "called\n"));

    if (1 != netsnmp_row_merge_status_first(reginfo, agtreq_info)) {
        DEBUGMSGTL(("internal:tcpConnectionTable",
                    "skipping additional pre_request\n"));
        return SNMP_ERR_NOERROR;
    }

    rc = tcpConnectionTable_pre_request(tcpConnectionTable_if_ctx.
                                        user_ctx);
    if (MFD_SUCCESS != rc) {
        /*
         * nothing we can do about it but log it
         */
        DEBUGMSGTL(("tcpConnectionTable", "error %d from "
                    "tcpConnectionTable_pre_request\n", rc));
        netsnmp_request_set_error_all(requests, SNMP_VALIDATE_ERR(rc));
    }

    return SNMP_ERR_NOERROR;
}                               /* _mfd_tcpConnectionTable_pre_request */

/**
 * @internal
 * wrapper
 */
static int
_mfd_tcpConnectionTable_post_request(netsnmp_mib_handler *handler,
                                     netsnmp_handler_registration *reginfo,
                                     netsnmp_agent_request_info
                                     *agtreq_info,
                                     netsnmp_request_info *requests)
{
    tcpConnectionTable_rowreq_ctx *rowreq_ctx = (tcpConnectionTable_rowreq_ctx*)
        netsnmp_container_table_row_extract(requests);
    int             rc, packet_rc;

    DEBUGMSGTL(("internal:tcpConnectionTable:_mfd_tcpConnectionTable_post_request", "called\n"));

    /*
     * release row context, if deleted
     */
    if (rowreq_ctx && (rowreq_ctx->rowreq_flags & MFD_ROW_DELETED))
        tcpConnectionTable_release_rowreq_ctx(rowreq_ctx);

    /*
     * wait for last call before calling user
     */
    if (1 != netsnmp_row_merge_status_last(reginfo, agtreq_info)) {
        DEBUGMSGTL(("internal:tcpConnectionTable",
                    "waiting for last post_request\n"));
        return SNMP_ERR_NOERROR;
    }

    packet_rc = netsnmp_check_all_requests_error(agtreq_info->asp, 0);
    if ((MFD_SUCCESS != packet_rc) && tcpConnectionTable_dirty_get()) {
        /*
         * we shouldn't get here. the undo steps should also clear
         * the dirty flags.
         */
        snmp_log(LOG_WARNING,
                 "tcpConnectionTable dirty flag set in post_request "
                 "but status != SUCCESS.\n");
    }

    rc = tcpConnectionTable_post_request(tcpConnectionTable_if_ctx.
                                         user_ctx, packet_rc);
    if (MFD_SUCCESS != rc) {
        /*
         * nothing we can do about it but log it
         */
        DEBUGMSGTL(("tcpConnectionTable", "error %d from "
                    "tcpConnectionTable_post_request\n", rc));
    }

    return SNMP_ERR_NOERROR;
}                               /* _mfd_tcpConnectionTable_post_request */

/**
 * @internal
 * wrapper
 */
static int
_mfd_tcpConnectionTable_object_lookup(netsnmp_mib_handler *handler, netsnmp_handler_registration
                                      *reginfo, netsnmp_agent_request_info
                                      *agtreq_info,
                                      netsnmp_request_info *requests)
{
    int             rc = SNMP_ERR_NOERROR;
    tcpConnectionTable_rowreq_ctx *rowreq_ctx = (tcpConnectionTable_rowreq_ctx*)
        netsnmp_container_table_row_extract(requests);

    DEBUGMSGTL(("internal:tcpConnectionTable:_mfd_tcpConnectionTable_object_lookup", "called\n"));

    /*
     * get our context from mfd
     * tcpConnectionTable_interface_ctx *if_ctx =
     *             (tcpConnectionTable_interface_ctx *)reginfo->my_reg_void;
     */

    if (NULL == rowreq_ctx) {
        rc = SNMP_ERR_NOCREATION;
    }

    if (MFD_SUCCESS != rc)
        netsnmp_request_set_error_all(requests, rc);
    else
        tcpConnectionTable_row_prep(rowreq_ctx);

    return SNMP_VALIDATE_ERR(rc);
}                               /* _mfd_tcpConnectionTable_object_lookup */

/***********************************************************************
 *
 * GET processing
 *
 ***********************************************************************/
/*
 * @internal
 * Retrieve the value for a particular column
 */
NETSNMP_STATIC_INLINE int
_tcpConnectionTable_get_column(tcpConnectionTable_rowreq_ctx * rowreq_ctx,
                               netsnmp_variable_list * var, int column)
{
    int             rc = SNMPERR_SUCCESS;

    DEBUGMSGTL(("internal:tcpConnectionTable:_mfd_tcpConnectionTable_get_column", "called for %d\n", column));


    netsnmp_assert(NULL != rowreq_ctx);

    switch (column) {

        /*
         * tcpConnectionState(7)/INTEGER/ASN_INTEGER/long(u_long)//l/A/W/E/r/d/h 
         */
    case COLUMN_TCPCONNECTIONSTATE:
        var->val_len = sizeof(u_long);
        var->type = ASN_INTEGER;
        rc = tcpConnectionState_get(rowreq_ctx,
                                    (u_long *) var->val.string);
        break;

        /*
         * tcpConnectionProcess(8)/UNSIGNED32/ASN_UNSIGNED/u_long(u_long)//l/A/w/e/r/d/h 
         */
    case COLUMN_TCPCONNECTIONPROCESS:
        var->val_len = sizeof(u_long);
        var->type = ASN_UNSIGNED;
        rc = tcpConnectionProcess_get(rowreq_ctx,
                                      (u_long *) var->val.string);
        break;

    default:
        snmp_log(LOG_ERR,
                 "unknown column %d in _tcpConnectionTable_get_column\n",
                 column);
        break;
    }

    return rc;
}                               /* _tcpConnectionTable_get_column */

int
_mfd_tcpConnectionTable_get_values(netsnmp_mib_handler *handler,
                                   netsnmp_handler_registration *reginfo,
                                   netsnmp_agent_request_info *agtreq_info,
                                   netsnmp_request_info *requests)
{
    tcpConnectionTable_rowreq_ctx *rowreq_ctx = (tcpConnectionTable_rowreq_ctx*)
        netsnmp_container_table_row_extract(requests);
    netsnmp_table_request_info *tri;
    u_char         *old_string;
    void            (*dataFreeHook) (void *);
    int             rc;

    DEBUGMSGTL(("internal:tcpConnectionTable:_mfd_tcpConnectionTable_get_values", "called\n"));

    netsnmp_assert(NULL != rowreq_ctx);

    for (; requests; requests = requests->next) {
        /*
         * save old pointer, so we can free it if replaced
         */
        old_string = requests->requestvb->val.string;
        dataFreeHook = requests->requestvb->dataFreeHook;
        if (NULL == requests->requestvb->val.string) {
            requests->requestvb->val.string = requests->requestvb->buf;
            requests->requestvb->val_len =
                sizeof(requests->requestvb->buf);
        } else if (requests->requestvb->buf ==
                   requests->requestvb->val.string) {
            if (requests->requestvb->val_len !=
                sizeof(requests->requestvb->buf))
                requests->requestvb->val_len =
                    sizeof(requests->requestvb->buf);
        }

        /*
         * get column data
         */
        tri = netsnmp_extract_table_info(requests);
        if (NULL == tri)
            continue;

        rc = _tcpConnectionTable_get_column(rowreq_ctx,
                                            requests->requestvb,
                                            tri->colnum);
        if (rc) {
            if (MFD_SKIP == rc) {
                requests->requestvb->type = SNMP_NOSUCHINSTANCE;
                rc = SNMP_ERR_NOERROR;
            }
        } else if (NULL == requests->requestvb->val.string) {
            snmp_log(LOG_ERR, "NULL varbind data pointer!\n");
            rc = SNMP_ERR_GENERR;
        }
        if (rc)
            netsnmp_request_set_error(requests, SNMP_VALIDATE_ERR(rc));

        /*
         * if the buffer wasn't used previously for the old data (i.e. it
         * was allcoated memory)  and the get routine replaced the pointer,
         * we need to free the previous pointer.
         */
        if (old_string && (old_string != requests->requestvb->buf) &&
            (requests->requestvb->val.string != old_string)) {
            if (dataFreeHook)
                (*dataFreeHook) (old_string);
            else
                free(old_string);
        }
    }                           /* for results */

    return SNMP_ERR_NOERROR;
}                               /* _mfd_tcpConnectionTable_get_values */


#ifndef NETSNMP_DISABLE_SET_SUPPORT
/***********************************************************************
 *
 * SET processing
 *
 ***********************************************************************/

/*----------------------------------------------------------------------
 *
 * SET: Syntax checks
 *
 *---------------------------------------------------------------------*/
/*
 * @internal
 * Check the syntax for a particular column
 */
NETSNMP_STATIC_INLINE int
_tcpConnectionTable_check_column(tcpConnectionTable_rowreq_ctx *
                                 rowreq_ctx, netsnmp_variable_list * var,
                                 int column)
{
    int             rc = SNMPERR_SUCCESS;

    DEBUGMSGTL(("internal:tcpConnectionTable:_tcpConnectionTable_check_column", "called for %d\n", column));

    netsnmp_assert(NULL != rowreq_ctx);

    switch (column) {
        /*
         * (INDEX) tcpConnectionLocalAddressType(1)/InetAddressType/ASN_INTEGER/long(u_long)//l/a/w/E/r/d/h 
         */
    case COLUMN_TCPCONNECTIONLOCALADDRESSTYPE:
        rc = SNMP_ERR_NOTWRITABLE;      /* can not change index of active row */
        break;
        /*
         * (INDEX) tcpConnectionLocalAddress(2)/InetAddress/ASN_OCTET_STR/char(char)//L/a/w/e/R/d/h 
         */
    case COLUMN_TCPCONNECTIONLOCALADDRESS:
        rc = SNMP_ERR_NOTWRITABLE;      /* can not change index of active row */
        break;
        /*
         * (INDEX) tcpConnectionLocalPort(3)/InetPortNumber/ASN_UNSIGNED/u_long(u_long)//l/a/w/e/R/d/H 
         */
    case COLUMN_TCPCONNECTIONLOCALPORT:
        rc = SNMP_ERR_NOTWRITABLE;      /* can not change index of active row */
        break;
        /*
         * (INDEX) tcpConnectionRemAddressType(4)/InetAddressType/ASN_INTEGER/long(u_long)//l/a/w/E/r/d/h 
         */
    case COLUMN_TCPCONNECTIONREMADDRESSTYPE:
        rc = SNMP_ERR_NOTWRITABLE;      /* can not change index of active row */
        break;
        /*
         * (INDEX) tcpConnectionRemAddress(5)/InetAddress/ASN_OCTET_STR/char(char)//L/a/w/e/R/d/h 
         */
    case COLUMN_TCPCONNECTIONREMADDRESS:
        rc = SNMP_ERR_NOTWRITABLE;      /* can not change index of active row */
        break;
        /*
         * (INDEX) tcpConnectionRemPort(6)/InetPortNumber/ASN_UNSIGNED/u_long(u_long)//l/a/w/e/R/d/H 
         */
    case COLUMN_TCPCONNECTIONREMPORT:
        rc = SNMP_ERR_NOTWRITABLE;      /* can not change index of active row */
        break;

        /*
         * tcpConnectionState(7)/INTEGER/ASN_INTEGER/long(u_long)//l/A/W/E/r/d/h 
         */
    case COLUMN_TCPCONNECTIONSTATE:
        rc = netsnmp_check_vb_type(var, ASN_INTEGER);
        /*
         * check that the value is one of defined enums 
         */
        if ((SNMPERR_SUCCESS == rc)
            && (*var->val.integer != TCPCONNECTIONSTATE_CLOSED)
            && (*var->val.integer != TCPCONNECTIONSTATE_LISTEN)
            && (*var->val.integer != TCPCONNECTIONSTATE_SYNSENT)
            && (*var->val.integer != TCPCONNECTIONSTATE_SYNRECEIVED)
            && (*var->val.integer != TCPCONNECTIONSTATE_ESTABLISHED)
            && (*var->val.integer != TCPCONNECTIONSTATE_FINWAIT1)
            && (*var->val.integer != TCPCONNECTIONSTATE_FINWAIT2)
            && (*var->val.integer != TCPCONNECTIONSTATE_CLOSEWAIT)
            && (*var->val.integer != TCPCONNECTIONSTATE_LASTACK)
            && (*var->val.integer != TCPCONNECTIONSTATE_CLOSING)
            && (*var->val.integer != TCPCONNECTIONSTATE_TIMEWAIT)
            && (*var->val.integer != TCPCONNECTIONSTATE_DELETETCB)
            ) {
            rc = SNMP_ERR_WRONGVALUE;
        }
        if (SNMPERR_SUCCESS != rc) {
            DEBUGMSGTL(("tcpConnectionTable:_tcpConnectionTable_check_column:tcpConnectionState", "varbind validation failed (eg bad type or size)\n"));
        } else {
            rc = tcpConnectionState_check_value(rowreq_ctx,
                                                *((u_long *) var->val.
                                                  string));
            if ((MFD_SUCCESS != rc) && (MFD_NOT_VALID_EVER != rc)
                && (MFD_NOT_VALID_NOW != rc)) {
                snmp_log(LOG_ERR,
                         "bad rc %d from tcpConnectionState_check_value\n",
                         rc);
                rc = SNMP_ERR_GENERR;
            }
        }
        break;

        /*
         * tcpConnectionProcess(8)/UNSIGNED32/ASN_UNSIGNED/u_long(u_long)//l/A/w/e/r/d/h 
         */
    case COLUMN_TCPCONNECTIONPROCESS:
        rc = SNMP_ERR_NOTWRITABLE;
        break;

    default:   /** We shouldn't get here */
        rc = SNMP_ERR_GENERR;
        snmp_log(LOG_ERR,
                 "unknown column %d in _tcpConnectionTable_check_column\n",
                 column);
    }

    return rc;
}                               /* _tcpConnectionTable_check_column */

int
_mfd_tcpConnectionTable_check_objects(netsnmp_mib_handler *handler, netsnmp_handler_registration
                                      *reginfo, netsnmp_agent_request_info
                                      *agtreq_info,
                                      netsnmp_request_info *requests)
{
    tcpConnectionTable_rowreq_ctx *rowreq_ctx = (tcpConnectionTable_rowreq_ctx*)
        netsnmp_container_table_row_extract(requests);
    netsnmp_table_request_info *tri;
    int             rc;

    DEBUGMSGTL(("internal:tcpConnectionTable:_mfd_tcpConnectionTable_check_objects", "called\n"));

    netsnmp_assert(NULL != rowreq_ctx);

    for (; requests; requests = requests->next) {

        /*
         * get column number from table request info, and check that column
         */
        tri = netsnmp_extract_table_info(requests);
        if (NULL == tri)
            continue;

        rc = _tcpConnectionTable_check_column(rowreq_ctx,
                                              requests->requestvb,
                                              tri->colnum);
        if (rc) {
            netsnmp_request_set_error(requests, SNMP_VALIDATE_ERR(rc));
            break;
        }

    }                           /* for results */

    return SNMP_ERR_NOERROR;
}                               /* _mfd_tcpConnectionTable_check_objects */


/*----------------------------------------------------------------------
 *
 * SET: check dependencies
 *
 *---------------------------------------------------------------------*/
/*
 * @internal
 * Check dependencies wrapper
 */
static int
_mfd_tcpConnectionTable_check_dependencies(netsnmp_mib_handler *handler, netsnmp_handler_registration
                                           *reginfo, netsnmp_agent_request_info
                                           *agtreq_info,
                                           netsnmp_request_info *requests)
{
    int             rc;
    tcpConnectionTable_rowreq_ctx *rowreq_ctx = (tcpConnectionTable_rowreq_ctx*)
        netsnmp_container_table_row_extract(requests);
    DEBUGMSGTL(("internal:tcpConnectionTable:_mfd_tcpConnectionTable_check_dependencies", "called\n"));

    netsnmp_assert(NULL != rowreq_ctx);

    rc = tcpConnectionTable_check_dependencies(rowreq_ctx);
    if (rc) {
        DEBUGMSGTL(("tcpConnectionTable:mfd", "error %d from "
                    "tcpConnectionTable_check_dependencies\n", rc));
        netsnmp_request_set_error_all(requests, SNMP_VALIDATE_ERR(rc));
    }

    return SNMP_ERR_NOERROR;
}                               /* _mfd_tcpConnectionTable_check_dependencies */

/*----------------------------------------------------------------------
 *
 * SET: Undo setup
 *
 *---------------------------------------------------------------------*/
/*
 * @internal
 * Set the value for a particular column
 */
NETSNMP_STATIC_INLINE int
_tcpConnectionTable_undo_setup_column(tcpConnectionTable_rowreq_ctx *
                                      rowreq_ctx, int column)
{
    int             rc = SNMPERR_SUCCESS;

    DEBUGMSGTL(("internal:tcpConnectionTable:_tcpConnectionTable_undo_setup_column", "called for %d\n", column));

    netsnmp_assert(NULL != rowreq_ctx);

    switch (column) {

        /*
         * tcpConnectionState(7)/INTEGER/ASN_INTEGER/long(u_long)//l/A/W/E/r/d/h 
         */
    case COLUMN_TCPCONNECTIONSTATE:
        rowreq_ctx->column_set_flags |= COLUMN_TCPCONNECTIONSTATE_FLAG;
        rc = tcpConnectionState_undo_setup(rowreq_ctx);
        break;

    default:
        snmp_log(LOG_ERR,
                 "unknown column %d in _tcpConnectionTable_undo_setup_column\n",
                 column);
        break;
    }

    return rc;
}                               /* _tcpConnectionTable_undo_setup_column */


/**
 * @internal
 * undo setup
 */
int
_mfd_tcpConnectionTable_undo_setup(netsnmp_mib_handler *handler,
                                   netsnmp_handler_registration *reginfo,
                                   netsnmp_agent_request_info *agtreq_info,
                                   netsnmp_request_info *requests)
{
    int             rc;
    tcpConnectionTable_rowreq_ctx *rowreq_ctx = (tcpConnectionTable_rowreq_ctx*)
        netsnmp_container_table_row_extract(requests);

    DEBUGMSGTL(("internal:tcpConnectionTable:_mfd_tcpConnectionTable_undo_setup", "called\n"));

    netsnmp_assert(NULL != rowreq_ctx);

    /*
     * allocate undo context
     */
    rowreq_ctx->undo = tcpConnectionTable_allocate_data();
    if (NULL == rowreq_ctx->undo) {
        /** msg already logged */
        netsnmp_request_set_error_all(requests,
                                      SNMP_ERR_RESOURCEUNAVAILABLE);
        return SNMP_ERR_NOERROR;
    }

    /*
     * row undo setup
     */
    rowreq_ctx->column_set_flags = 0;
    rc = tcpConnectionTable_undo_setup(rowreq_ctx);
    if (MFD_SUCCESS != rc) {
        DEBUGMSGTL(("tcpConnectionTable:mfd", "error %d from "
                    "tcpConnectionTable_undo_setup\n", rc));
        netsnmp_request_set_error_all(requests, SNMP_VALIDATE_ERR(rc));
    } else {
        /*
         * column undo setup
         */
        netsnmp_table_request_info *tri;
        for (; requests; requests = requests->next) {
            /*
             * set column data
             */
            tri = netsnmp_extract_table_info(requests);
            if (NULL == tri)
                continue;

            rc = _tcpConnectionTable_undo_setup_column(rowreq_ctx,
                                                       tri->colnum);
            if (MFD_SUCCESS != rc) {
                DEBUGMSGTL(("tcpConnectionTable:mfd", "error %d from "
                            "tcpConnectionTable_undo_setup_column\n", rc));
                netsnmp_set_request_error(agtreq_info, requests,
                                          SNMP_VALIDATE_ERR(rc));
            }
        }                       /* for results */
    }

    return SNMP_ERR_NOERROR;
}                               /* _mfd_tcpConnectionTable_undo_setup */

/**
 * @internal
 * undo setup
 */
int
_mfd_tcpConnectionTable_undo_cleanup(netsnmp_mib_handler *handler,
                                     netsnmp_handler_registration *reginfo,
                                     netsnmp_agent_request_info
                                     *agtreq_info,
                                     netsnmp_request_info *requests)
{
    tcpConnectionTable_rowreq_ctx *rowreq_ctx = (tcpConnectionTable_rowreq_ctx*)
        netsnmp_container_table_row_extract(requests);
    int             rc;

    DEBUGMSGTL(("internal:tcpConnectionTable:_mfd_tcpConnectionTable_undo_cleanup", "called\n"));

    /*
     * failed row create in early stages has no rowreq_ctx
     */
    if (NULL == rowreq_ctx)
        return MFD_SUCCESS;

    /*
     * call user cleanup
     */
    rc = tcpConnectionTable_undo_cleanup(rowreq_ctx);
    if (MFD_SUCCESS != rc) {
        /*
         * nothing we can do about it but log it
         */
        DEBUGMSGTL(("tcpConnectionTable:mfd", "error %d from "
                    "tcpConnectionTable_undo_cleanup\n", rc));
    }

    /*
     * release undo context, if needed
     */
    if (rowreq_ctx->undo) {
        tcpConnectionTable_release_data(rowreq_ctx->undo);
        rowreq_ctx->undo = NULL;
    }


    return SNMP_ERR_NOERROR;
}                               /* _mfd_tcpConnectionTable_undo_cleanup */

/*----------------------------------------------------------------------
 *
 * SET: Set values
 *
 *---------------------------------------------------------------------*/
/*
 * @internal
 * Set the value for a particular column
 */
NETSNMP_STATIC_INLINE int
_tcpConnectionTable_set_column(tcpConnectionTable_rowreq_ctx * rowreq_ctx,
                               netsnmp_variable_list * var, int column)
{
    int             rc = SNMPERR_SUCCESS;

    DEBUGMSGTL(("internal:tcpConnectionTable:_tcpConnectionTable_set_column", "called for %d\n", column));

    netsnmp_assert(NULL != rowreq_ctx);

    switch (column) {

        /*
         * tcpConnectionState(7)/INTEGER/ASN_INTEGER/long(u_long)//l/A/W/E/r/d/h 
         */
    case COLUMN_TCPCONNECTIONSTATE:
        rowreq_ctx->column_set_flags |= COLUMN_TCPCONNECTIONSTATE_FLAG;
        rc = tcpConnectionState_set(rowreq_ctx,
                                    *((u_long *) var->val.string));
        break;

    default:
        snmp_log(LOG_ERR,
                 "unknown column %d in _tcpConnectionTable_set_column\n",
                 column);
        rc = SNMP_ERR_GENERR;
        break;
    }

    return rc;
}                               /* _tcpConnectionTable_set_column */

int
_mfd_tcpConnectionTable_set_values(netsnmp_mib_handler *handler,
                                   netsnmp_handler_registration *reginfo,
                                   netsnmp_agent_request_info *agtreq_info,
                                   netsnmp_request_info *requests)
{
    tcpConnectionTable_rowreq_ctx *rowreq_ctx = (tcpConnectionTable_rowreq_ctx*)
        netsnmp_container_table_row_extract(requests);
    netsnmp_table_request_info *tri;
    int             rc = SNMP_ERR_NOERROR;

    DEBUGMSGTL(("internal:tcpConnectionTable:_mfd_tcpConnectionTable_set_values", "called\n"));

    netsnmp_assert(NULL != rowreq_ctx);

    rowreq_ctx->column_set_flags = 0;
    for (; requests; requests = requests->next) {
        /*
         * set column data
         */
        tri = netsnmp_extract_table_info(requests);
        if (NULL == tri)
            continue;

        rc = _tcpConnectionTable_set_column(rowreq_ctx,
                                            requests->requestvb,
                                            tri->colnum);
        if (MFD_SUCCESS != rc) {
            DEBUGMSGTL(("tcpConnectionTable:mfd", "error %d from "
                        "tcpConnectionTable_set_column\n", rc));
            netsnmp_set_request_error(agtreq_info, requests,
                                      SNMP_VALIDATE_ERR(rc));
        }
    }                           /* for results */

    return SNMP_ERR_NOERROR;
}                               /* _mfd_tcpConnectionTable_set_values */

/*----------------------------------------------------------------------
 *
 * SET: commit
 *
 *---------------------------------------------------------------------*/
/**
 * @internal
 * commit the values
 */
int
_mfd_tcpConnectionTable_commit(netsnmp_mib_handler *handler,
                               netsnmp_handler_registration *reginfo,
                               netsnmp_agent_request_info *agtreq_info,
                               netsnmp_request_info *requests)
{
    int             rc;
    tcpConnectionTable_rowreq_ctx *rowreq_ctx = (tcpConnectionTable_rowreq_ctx*)
        netsnmp_container_table_row_extract(requests);

    DEBUGMSGTL(("internal:tcpConnectionTable:_mfd_tcpConnectionTable_commit", "called\n"));

    netsnmp_assert(NULL != rowreq_ctx);

    rc = tcpConnectionTable_commit(rowreq_ctx);
    if (MFD_SUCCESS != rc) {
        DEBUGMSGTL(("tcpConnectionTable:mfd", "error %d from "
                    "tcpConnectionTable_commit\n", rc));
        netsnmp_request_set_error_all(requests, SNMP_VALIDATE_ERR(rc));
    }

    if (rowreq_ctx->rowreq_flags & MFD_ROW_DIRTY) {
        /*
         * if we successfully commited this row, set the dirty flag. Use the
         * current value + 1 (i.e. dirty = # rows changed).
         * this is checked in post_request...
         */
        tcpConnectionTable_dirty_set(tcpConnectionTable_dirty_get() + 1);       /* set table dirty flag */
    }

    return SNMP_ERR_NOERROR;
}

int
_mfd_tcpConnectionTable_undo_commit(netsnmp_mib_handler *handler,
                                    netsnmp_handler_registration *reginfo,
                                    netsnmp_agent_request_info
                                    *agtreq_info,
                                    netsnmp_request_info *requests)
{
    int             rc;
    tcpConnectionTable_rowreq_ctx *rowreq_ctx = (tcpConnectionTable_rowreq_ctx*)
        netsnmp_container_table_row_extract(requests);

    DEBUGMSGTL(("internal:tcpConnectionTable:_mfd_tcpConnectionTable_undo_commit", "called\n"));

    netsnmp_assert(NULL != rowreq_ctx);

    if (rowreq_ctx->rowreq_flags & MFD_ROW_DIRTY) {
        u_int           d = tcpConnectionTable_dirty_get();

        netsnmp_assert(d != 0);
        if (d)
            tcpConnectionTable_dirty_set(d - 1);
    }

    rc = tcpConnectionTable_undo_commit(rowreq_ctx);
    if (MFD_SUCCESS != rc) {
        /*
         * nothing we can do about it but log it
         */
        DEBUGMSGTL(("tcpConnectionTable:mfd", "error %d from "
                    "tcpConnectionTable_undo_commit\n", rc));
    }

    if (rowreq_ctx->rowreq_flags & MFD_ROW_DIRTY) {
        snmp_log(LOG_WARNING,
                 "tcpConnectionTable row dirty flag still set after undo_commit\n");
        rowreq_ctx->rowreq_flags &= ~MFD_ROW_DIRTY;
    }

    return SNMP_ERR_NOERROR;
}                               /* _mfd_tcpConnectionTable_commit */

/*----------------------------------------------------------------------
 *
 * SET: Undo
 *
 *---------------------------------------------------------------------*/
/**
 * @internal
 * undo the value for a particular column
 */
NETSNMP_STATIC_INLINE int
_tcpConnectionTable_undo_column(tcpConnectionTable_rowreq_ctx * rowreq_ctx,
                                netsnmp_variable_list * var, int column)
{
    int             rc = SNMPERR_SUCCESS;

    DEBUGMSGTL(("internal:tcpConnectionTable:_tcpConnectionTable_undo_column", "called for %d\n", column));

    netsnmp_assert(NULL != rowreq_ctx);

    switch (column) {

        /*
         * tcpConnectionState(7)/INTEGER/ASN_INTEGER/long(u_long)//l/A/W/E/r/d/h 
         */
    case COLUMN_TCPCONNECTIONSTATE:
        rc = tcpConnectionState_undo(rowreq_ctx);
        break;

    default:
        snmp_log(LOG_ERR,
                 "unknown column %d in _tcpConnectionTable_undo_column\n",
                 column);
        break;
    }

    return rc;
}                               /* _tcpConnectionTable_undo_column */

int
_mfd_tcpConnectionTable_undo_values(netsnmp_mib_handler *handler,
                                    netsnmp_handler_registration *reginfo,
                                    netsnmp_agent_request_info
                                    *agtreq_info,
                                    netsnmp_request_info *requests)
{
    int             rc;
    tcpConnectionTable_rowreq_ctx *rowreq_ctx = (tcpConnectionTable_rowreq_ctx*)
        netsnmp_container_table_row_extract(requests);
    netsnmp_table_request_info *tri;

    DEBUGMSGTL(("internal:tcpConnectionTable:_mfd_tcpConnectionTable_undo_values", "called\n"));

    netsnmp_assert(NULL != rowreq_ctx);

    rc = tcpConnectionTable_undo(rowreq_ctx);
    if (MFD_SUCCESS != rc) {
        /*
         * nothing we can do about it but log it
         */
        DEBUGMSGTL(("tcpConnectionTable:mfd", "error %d from "
                    "tcpConnectionTable_undo\n", rc));
    }

    for (; requests; requests = requests->next) {
        /*
         * set column data
         */
        tri = netsnmp_extract_table_info(requests);
        if (NULL == tri)
            continue;

        rc = _tcpConnectionTable_undo_column(rowreq_ctx,
                                             requests->requestvb,
                                             tri->colnum);
        if (MFD_SUCCESS != rc) {
            /*
             * nothing we can do about it but log it
             */
            DEBUGMSGTL(("tcpConnectionTable:mfd", "error %d from "
                        "tcpConnectionTable_undo_column\n", rc));
        }
    }                           /* for results */

    return SNMP_ERR_NOERROR;
}                               /* _mfd_tcpConnectionTable_undo_values */

/*----------------------------------------------------------------------
 *
 * SET: irreversible commit
 *
 *---------------------------------------------------------------------*/
/**
 * @internal
 * commit irreversible actions
 */
int
_mfd_tcpConnectionTable_irreversible_commit(netsnmp_mib_handler *handler, netsnmp_handler_registration
                                            *reginfo, netsnmp_agent_request_info
                                            *agtreq_info,
                                            netsnmp_request_info *requests)
{
    tcpConnectionTable_rowreq_ctx *rowreq_ctx = (tcpConnectionTable_rowreq_ctx*)
        netsnmp_container_table_row_extract(requests);

    DEBUGMSGTL(("internal:tcpConnectionTable:_mfd_tcpConnectionTable_irreversible:commit", "called\n"));

    netsnmp_assert(NULL != rowreq_ctx);

    /*
     * check for and handle row creation/deletion
     * and update column exist flags...
     */
    if (rowreq_ctx->rowreq_flags & MFD_ROW_DELETED) {
        CONTAINER_REMOVE(tcpConnectionTable_if_ctx.container, rowreq_ctx);
    } else {
        if (rowreq_ctx->column_set_flags) {
            rowreq_ctx->column_set_flags = 0;
        }
    }

    return SNMP_ERR_NOERROR;
}                               /* _mfd_tcpConnectionTable_irreversible_commit */
#endif

/***********************************************************************
 *
 * DATA ACCESS
 *
 ***********************************************************************/
static void     _container_free(netsnmp_container *container);

/**
 * @internal
 */
static int
_cache_load(netsnmp_cache * cache, void *vmagic)
{
    DEBUGMSGTL(("internal:tcpConnectionTable:_cache_load", "called\n"));

    if ((NULL == cache) || (NULL == cache->magic)) {
        snmp_log(LOG_ERR,
                 "invalid cache for tcpConnectionTable_cache_load\n");
        return -1;
    }

    /** should only be called for an invalid or expired cache */
    netsnmp_assert((0 == cache->valid) || (1 == cache->expired));

    /*
     * call user code
     */
    return tcpConnectionTable_container_load((netsnmp_container *) cache->
                                             magic);
}                               /* _cache_load */

/**
 * @internal
 */
static void
_cache_free(netsnmp_cache * cache, void *magic)
{
    netsnmp_container *container;

    DEBUGMSGTL(("internal:tcpConnectionTable:_cache_free", "called\n"));

    if ((NULL == cache) || (NULL == cache->magic)) {
        snmp_log(LOG_ERR,
                 "invalid cache in tcpConnectionTable_cache_free\n");
        return;
    }

    container = (netsnmp_container *) cache->magic;

    _container_free(container);
}                               /* _cache_free */

/**
 * @internal
 */
static void
_container_item_free(tcpConnectionTable_rowreq_ctx * rowreq_ctx,
                     void *context)
{
    DEBUGMSGTL(("internal:tcpConnectionTable:_container_item_free",
                "called\n"));

    if (NULL == rowreq_ctx)
        return;

    tcpConnectionTable_release_rowreq_ctx(rowreq_ctx);
}                               /* _container_item_free */

/**
 * @internal
 */
static void
_container_free(netsnmp_container *container)
{
    DEBUGMSGTL(("internal:tcpConnectionTable:_container_free",
                "called\n"));

    if (NULL == container) {
        snmp_log(LOG_ERR,
                 "invalid container in tcpConnectionTable_container_free\n");
        return;
    }

    /*
     * call user code
     */
    tcpConnectionTable_container_free(container);

    /*
     * free all items. inefficient, but easy.
     */
    CONTAINER_CLEAR(container,
                    (netsnmp_container_obj_func *) _container_item_free,
                    NULL);
}                               /* _container_free */

/**
 * @internal
 * initialize the container with functions or wrappers
 */
void
_tcpConnectionTable_container_init(tcpConnectionTable_interface_ctx *
                                   if_ctx)
{
    DEBUGMSGTL(("internal:tcpConnectionTable:_tcpConnectionTable_container_init", "called\n"));

    /*
     * cache init
     */
    if_ctx->cache = netsnmp_cache_create(30,    /* timeout in seconds */
                                         _cache_load, _cache_free,
                                         tcpConnectionTable_oid,
                                         tcpConnectionTable_oid_size);

    if (NULL == if_ctx->cache) {
        snmp_log(LOG_ERR, "error creating cache for tcpConnectionTable\n");
        return;
    }

    if_ctx->cache->flags = NETSNMP_CACHE_DONT_INVALIDATE_ON_SET;

    tcpConnectionTable_container_init(&if_ctx->container, if_ctx->cache);
    if (NULL == if_ctx->container) {
        if_ctx->container =
            netsnmp_container_find("tcpConnectionTable:table_container");
        if (if_ctx->container)
        if_ctx->container->container_name = strdup("tcpConnectionTable");
    }
    if (NULL == if_ctx->container) {
        snmp_log(LOG_ERR, "error creating container in "
                 "tcpConnectionTable_container_init\n");
        return;
    }

    if (NULL != if_ctx->cache)
        if_ctx->cache->magic = (void *) if_ctx->container;
}                               /* _tcpConnectionTable_container_init */

/**
 * @internal
 * shutdown the container with functions or wrappers
 */
void
_tcpConnectionTable_container_shutdown(tcpConnectionTable_interface_ctx *
                                       if_ctx)
{
    DEBUGMSGTL(("internal:tcpConnectionTable:_tcpConnectionTable_container_shutdown", "called\n"));

    tcpConnectionTable_container_shutdown(if_ctx->container);

    _container_free(if_ctx->container);

}                               /* _tcpConnectionTable_container_shutdown */


tcpConnectionTable_rowreq_ctx *
tcpConnectionTable_row_find_by_mib_index(tcpConnectionTable_mib_index *
                                         mib_idx)
{
    tcpConnectionTable_rowreq_ctx *rowreq_ctx;
    oid             oid_tmp[MAX_OID_LEN];
    netsnmp_index   oid_idx;
    int             rc;

    /*
     * set up storage for OID
     */
    oid_idx.oids = oid_tmp;
    oid_idx.len = sizeof(oid_tmp) / sizeof(oid);

    /*
     * convert
     */
    rc = tcpConnectionTable_index_to_oid(&oid_idx, mib_idx);
    if (MFD_SUCCESS != rc)
        return NULL;

    rowreq_ctx = (tcpConnectionTable_rowreq_ctx*)
        CONTAINER_FIND(tcpConnectionTable_if_ctx.container, &oid_idx);

    return rowreq_ctx;
}
