/*
 * Note: this file originally auto-generated by mib2c using
 *       version : 1.48 $ of : mfd-top.m2c,v $ 
 *
 * $Id$
 */
/** \page MFD helper for ifXTable
 *
 * \section intro Introduction
 * Introductory text.
 *
 */
/*
 * 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 <ctype.h>

/*
 * include our parent header 
 */
#include "ifXTable.h"
#include "if-mib/ifTable/ifTable_defs.h"

#include <net-snmp/agent/mib_modules.h>

#include "ifXTable_interface.h"

/*
 * not sure if we want to support set for promiscuous mode, because
 * 1) careful thought should go into any settable object that performs
 *    an action that requires root access
 * 2) i don't want to write the code right now
 * 
 */
#undef NETSNMP_ENABLE_PROMISCUOUSMODE_SET

const oid       ifXTable_oid[] = { IFXTABLE_OID };
const int       ifXTable_oid_size = OID_LENGTH(ifXTable_oid);

ifXTable_registration ifXTable_user_context;
static ifXTable_registration *ifXTable_user_context_p;

/**
 * Initializes the ifXTable module
 */
void
init_ifXTable(void)
{
    DEBUGMSGTL(("verbose:ifXTable:init_ifXTable", "called\n"));

    /*
     * TODO:300:o: Perform ifXTable one-time module initialization.
     */

    /*
     * here we initialize all the tables we're planning on supporting
     */
    init_ifTable();

}                               /* init_ifXTable */

/**
 * Initialize the table ifXTable 
 *    (Define its contents and how it's structured)
 */
void
initialize_table_ifXTable(void)
{
    u_long          flags;

    DEBUGMSGTL(("verbose:ifXTable:initialize_table_ifXTable", "called\n"));

    /*
     * TODO:301:o: Perform ifXTable one-time table initialization.
     */

    /*
     * TODO:302:o: |->Initialize ifXTable user context
     * if you'd like to pass in a pointer to some data for this
     * table, allocate or set it up here.
     */
    /*
     * a netsnmp_data_list is a simple way to store void pointers. A simple
     * string token is used to add, find or remove pointers.
     */
    ifXTable_user_context_p = netsnmp_create_data_list("ifXTable", NULL, NULL);

    /*
     * No support for any flags yet, but in the future you would
     * set any flags here.
     */
    flags = 0;

    /*
     * call interface initialization code
     */
    _ifXTable_initialize_interface(ifXTable_user_context_p, flags);

    /*
     * if there is no container, bail. otherwise, register the callbacks
     * for persistent storage.
     */
    if (NULL == ifTable_container_get())
        return;                 /* msg already logged */

}                               /* initialize_table_ifXTable */

void
shutdown_ifXTable(void)
{
    netsnmp_free_all_list_data(ifXTable_user_context_p);
    ifXTable_user_context_p = NULL;
}

/**
 * extra context initialization (eg default values)
 *
 * @param rowreq_ctx    : row request context
 * @param user_init_ctx : void pointer for user (parameter to rowreq_ctx_allocate)
 *
 * @retval MFD_SUCCESS  : no errors
 * @retval MFD_ERROR    : error (context allocate will fail)
 */
int
ifXTable_rowreq_ctx_init(ifXTable_rowreq_ctx * rowreq_ctx,
                         void *user_init_ctx)
{
    DEBUGMSGTL(("verbose:ifXTable:ifXTable_rowreq_ctx_init", "called\n"));

    netsnmp_assert(NULL != rowreq_ctx);

    /*
     * TODO:210:o: |-> Perform extra ifXTable rowreq initialization. (eg DEFVALS)
     * should never get here - ifTable should handle this
     */
    netsnmp_assert(0);

    return MFD_ERROR;
}                               /* ifXTable_rowreq_ctx_init */

/**
 * extra context cleanup
 *
 */
void
ifXTable_rowreq_ctx_cleanup(ifXTable_rowreq_ctx * rowreq_ctx)
{
    DEBUGMSGTL(("verbose:ifXTable:ifXTable_rowreq_ctx_cleanup",
                "called\n"));

    netsnmp_assert(NULL != rowreq_ctx);

    /*
     * TODO:211:o: |-> Perform extra ifXTable rowreq cleanup.
     */
    /*
     * should never get here - ifTable should handle this
     */
    netsnmp_assert(0);
}                               /* ifXTable_rowreq_ctx_cleanup */

/**
 * the *_should_save routine is called to determine if a row
 * should be stored persistently.
 *
 * Note that this is not a 'dirty' check (i.e. if a row has changed),
 * but a check for volatile rows that should not be saved between
 * restarts.
 *
 * @param rowreq_ctx
 * 
 * @return 1 if the row should be stored
 * @return 0 if the row should not be stored
 */
int
ifXTable_container_should_save(ifXTable_rowreq_ctx * rowreq_ctx)
{

    return 1;                   /* save the row */
}

/**
 * pre-request callback
 *
 * @param user_context
 * @retval MFD_SUCCESS              : success.
 * @retval MFD_ERROR                : other error
 */
int
ifXTable_pre_request(ifXTable_registration * user_context)
{
    DEBUGMSGTL(("verbose:ifXTable:ifXTable_pre_request", "called\n"));

    /*
     * TODO:510:o: Perform ifXTable pre-request actions.
     */

    return MFD_SUCCESS;
}                               /* ifXTable_pre_request */

/**
 * post-request callback
 *
 * Note:
 *   New rows have been inserted into the container, and
 *   deleted rows have been removed from the container and
 *   released.
 *
 * @param user_context
 * @param rc : MFD_SUCCESS if all requests succeeded
 *
 * @retval MFD_SUCCESS : success.
 * @retval MFD_ERROR   : other error (ignored)
 */
int
ifXTable_post_request(ifXTable_registration * user_context, int rc)
{
    DEBUGMSGTL(("verbose:ifXTable:ifXTable_post_request", "called\n"));

    /*
     * TODO:511:o: Perform ifXTable post-request actions.
     */

    /*
     * check to set if any rows were changed.
     */
    if (ifXTable_dirty_get()) {
        /*
         * check if request was successful. If so, this would be
         * a good place to save data to its persistent store.
         */
        if (MFD_SUCCESS == rc) {
            /*
             * notify library to save changed rows
             */
            snmp_store_needed(netsnmp_ds_get_string(NETSNMP_DS_LIBRARY_ID,
                                             NETSNMP_DS_LIB_APPTYPE));
        }

        ifXTable_dirty_set(0);  /* clear table dirty flag */
    }

    return MFD_SUCCESS;
}                               /* ifXTable_post_request */


/**********************************************************************
 **********************************************************************
 ***
 *** Table ifXTable
 ***
 **********************************************************************
 **********************************************************************/
/*
 * IF-MIB::ifXTable is subid 1 of ifMIBObjects.
 * Its status is Current.
 * OID: .1.3.6.1.2.1.31.1.1, length: 9
 */

/*
 * ---------------------------------------------------------------------
 * * TODO:200:r: Implement ifXTable data context functions.
 */


/**
 * set mib index(es)
 *
 * @param tbl_idx mib index structure
 * @param ifIndex_val
 *
 * @retval MFD_SUCCESS     : success.
 * @retval MFD_ERROR       : other error.
 *
 * @remark
 *  This convenience function is useful for setting all the MIB index
 *  components with a single function call. It is assume that the C values
 *  have already been mapped from their native/rawformat to the MIB format.
 */
int
ifXTable_indexes_set_tbl_idx(ifXTable_mib_index * tbl_idx,
                             long ifIndex_val)
{
    DEBUGMSGTL(("verbose:ifXTable:ifXTable_indexes_set_tbl_idx",
                "called\n"));

    /*
     * ifIndex(1)/InterfaceIndex/ASN_INTEGER/long(long)//l/A/w/e/R/d/H 
     */
    tbl_idx->ifIndex = ifIndex_val;


    return MFD_SUCCESS;
}                               /* ifXTable_indexes_set_tbl_idx */

/**
 * @internal
 * set row context indexes
 *
 * @param reqreq_ctx the row context that needs updated indexes
 * @param ifIndex_val
 *
 * @retval MFD_SUCCESS     : success.
 * @retval MFD_ERROR       : other error.
 *
 * @remark
 *  This function sets the mib indexs, then updates the oid indexs
 *  from the mib index.
 */
int
ifXTable_indexes_set(ifXTable_rowreq_ctx * rowreq_ctx, long ifIndex_val)
{
    DEBUGMSGTL(("verbose:ifXTable:ifXTable_indexes_set", "called\n"));

    if (MFD_SUCCESS !=
        ifXTable_indexes_set_tbl_idx(&rowreq_ctx->tbl_idx, ifIndex_val))
        return MFD_ERROR;

    /*
     * convert mib index to oid index
     */
    rowreq_ctx->oid_idx.len = sizeof(rowreq_ctx->oid_tmp) / sizeof(oid);
    if (0 != ifXTable_index_to_oid(&rowreq_ctx->oid_idx,
                                   &rowreq_ctx->tbl_idx)) {
        return MFD_ERROR;
    }

    return MFD_SUCCESS;
}                               /* ifXTable_indexes_set */


/*---------------------------------------------------------------------
 * IF-MIB::ifXEntry.ifName
 * ifName is subid 1 of ifXEntry.
 * Its status is Current, and its access level is ReadOnly.
 * OID: .1.3.6.1.2.1.31.1.1.1.1
 * Description:
The textual name of the interface.  The value of this
            object should be the name of the interface as assigned by
            the local device and should be suitable for use in commands
            entered at the device's `console'.  This might be a text
            name, such as `le0' or a simple port number, such as `1',
            depending on the interface naming syntax of the device.  If
            several entries in the ifTable together represent a single
            interface as named by the device, then each will have the
            same value of ifName.  Note that for an agent which responds
            to SNMP queries concerning an interface on some other
            (proxied) device, then the value of ifName for such an
            interface is the proxied device's local name for it.

            If there is no local name, or this object is otherwise not
            applicable, then this object contains a zero-length string.
 *
 * Attributes:
 *   accessible 1     isscalar 0     enums  0      hasdefval 0
 *   readable   1     iscolumn 1     ranges 1      hashint   1
 *   settable   0
 *   hint: 255a
 *
 * Ranges:  0 - 255;
 *
 * Its syntax is DisplayString (based on perltype OCTETSTR)
 * The net-snmp type is ASN_OCTET_STR. The C type decl is char (char)
 * This data type requires a length.  (Max 255)
 */
/**
 * Extract the current value of the ifName data.
 *
 * Set a value using the data context for the row.
 *
 * @param rowreq_ctx
 *        Pointer to the row request context.
 * @param ifName_val_ptr_ptr
 *        Pointer to storage for a char variable
 * @param ifName_val_ptr_len_ptr
 *        Pointer to a size_t. On entry, it will contain the size (in bytes)
 *        pointed to by ifName.
 *        On exit, this value should contain the data size (in bytes).
 *
 * @retval MFD_SUCCESS         : success
 * @retval MFD_SKIP            : skip this node (no value for now)
 * @retval MFD_ERROR           : Any other error
*
 * @note If you need more than (*ifName_val_ptr_len_ptr) bytes of memory,
 *       allocate it using malloc() and update ifName_val_ptr_ptr.
 *       <b>DO NOT</b> free the previous pointer.
 *       The MFD helper will release the memory you allocate.
 *
 * @remark If you call this function yourself, you are responsible
 *         for checking if the pointer changed, and freeing any
 *         previously allocated memory. (Not necessary if you pass
 *         in a pointer to static memory, obviously.)
 */
int
ifName_get(ifXTable_rowreq_ctx * rowreq_ctx, char **ifName_val_ptr_ptr,
           size_t * ifName_val_ptr_len_ptr)
{
    size_t tmp_len;

   /** we should have a non-NULL pointer and enough storage */
    netsnmp_assert((NULL != ifName_val_ptr_ptr)
                   && (NULL != *ifName_val_ptr_ptr));
    netsnmp_assert(NULL != ifName_val_ptr_len_ptr);


    DEBUGMSGTL(("verbose:ifXTable:ifName_get", "called\n"));

    netsnmp_assert(NULL != rowreq_ctx);

    /*
     * TODO:231:o: |-> Extract the current value of the ifName data.
     * copy (* ifName_val_ptr_ptr ) data and (* ifName_val_ptr_len_ptr ) from rowreq_ctx->data
     */
    /*
     * make sure there is enough space for ifName data
     */
    tmp_len = strlen(rowreq_ctx->data.ifName);
    if ((NULL == (*ifName_val_ptr_ptr)) ||
        ((*ifName_val_ptr_len_ptr) < tmp_len)) {
        /*
         * allocate space for ifName data
         */
        (*ifName_val_ptr_ptr) = (char*)malloc(tmp_len);
        if (NULL == (*ifName_val_ptr_ptr)) {
            snmp_log(LOG_ERR, "could not allocate memory\n");
            return MFD_ERROR;
        }
    }
    (*ifName_val_ptr_len_ptr) = tmp_len;
    memcpy((*ifName_val_ptr_ptr), rowreq_ctx->data.ifName, tmp_len);

    return MFD_SUCCESS;
}                               /* ifName_get */

/*---------------------------------------------------------------------
 * IF-MIB::ifXEntry.ifInMulticastPkts
 * ifInMulticastPkts is subid 2 of ifXEntry.
 * Its status is Current, and its access level is ReadOnly.
 * OID: .1.3.6.1.2.1.31.1.1.1.2
 * Description:
The number of packets, delivered by this sub-layer to a
            higher (sub-)layer, which were addressed to a multicast
            address at this sub-layer.  For a MAC layer protocol, this
            includes both Group and Functional addresses.

            Discontinuities in the value of this counter can occur at
            re-initialization of the management system, and at other

            times as indicated by the value of
            ifCounterDiscontinuityTime.
 *
 * Attributes:
 *   accessible 1     isscalar 0     enums  0      hasdefval 0
 *   readable   1     iscolumn 1     ranges 0      hashint   0
 *   settable   0
 *
 *
 * Its syntax is COUNTER (based on perltype COUNTER)
 * The net-snmp type is ASN_COUNTER. The C type decl is u_long (u_long)
 */
/**
 * Extract the current value of the ifInMulticastPkts data.
 *
 * Set a value using the data context for the row.
 *
 * @param rowreq_ctx
 *        Pointer to the row request context.
 * @param ifInMulticastPkts_val_ptr
 *        Pointer to storage for a u_long variable
 *
 * @retval MFD_SUCCESS         : success
 * @retval MFD_SKIP            : skip this node (no value for now)
 * @retval MFD_ERROR           : Any other error
 */
int
ifInMulticastPkts_get(ifXTable_rowreq_ctx * rowreq_ctx,
                      u_long * ifInMulticastPkts_val_ptr)
{
   /** we should have a non-NULL pointer */
    netsnmp_assert(NULL != ifInMulticastPkts_val_ptr);


    DEBUGMSGTL(("verbose:ifXTable:ifInMulticastPkts_get", "called\n"));

    netsnmp_assert(NULL != rowreq_ctx);

    /*
     * TODO:231:o: |-> Extract the current value of the ifInMulticastPkts data.
     * copy (* ifInMulticastPkts_val_ptr ) from rowreq_ctx->data
     */
    (*ifInMulticastPkts_val_ptr) = rowreq_ctx->data.ifInMulticastPkts;

    return MFD_SUCCESS;
}                               /* ifInMulticastPkts_get */

/*---------------------------------------------------------------------
 * IF-MIB::ifXEntry.ifInBroadcastPkts
 * ifInBroadcastPkts is subid 3 of ifXEntry.
 * Its status is Current, and its access level is ReadOnly.
 * OID: .1.3.6.1.2.1.31.1.1.1.3
 * Description:
The number of packets, delivered by this sub-layer to a
            higher (sub-)layer, which were addressed to a broadcast
            address at this sub-layer.

            Discontinuities in the value of this counter can occur at
            re-initialization of the management system, and at other
            times as indicated by the value of
            ifCounterDiscontinuityTime.
 *
 * Attributes:
 *   accessible 1     isscalar 0     enums  0      hasdefval 0
 *   readable   1     iscolumn 1     ranges 0      hashint   0
 *   settable   0
 *
 *
 * Its syntax is COUNTER (based on perltype COUNTER)
 * The net-snmp type is ASN_COUNTER. The C type decl is u_long (u_long)
 */
/**
 * Extract the current value of the ifInBroadcastPkts data.
 *
 * Set a value using the data context for the row.
 *
 * @param rowreq_ctx
 *        Pointer to the row request context.
 * @param ifInBroadcastPkts_val_ptr
 *        Pointer to storage for a u_long variable
 *
 * @retval MFD_SUCCESS         : success
 * @retval MFD_SKIP            : skip this node (no value for now)
 * @retval MFD_ERROR           : Any other error
 */
int
ifInBroadcastPkts_get(ifXTable_rowreq_ctx * rowreq_ctx,
                      u_long * ifInBroadcastPkts_val_ptr)
{
   /** we should have a non-NULL pointer */
    netsnmp_assert(NULL != ifInBroadcastPkts_val_ptr);


    DEBUGMSGTL(("verbose:ifXTable:ifInBroadcastPkts_get", "called\n"));

    netsnmp_assert(NULL != rowreq_ctx);

    /*
     * TODO:231:o: |-> Extract the current value of the ifInBroadcastPkts data.
     * copy (* ifInBroadcastPkts_val_ptr ) from rowreq_ctx->data
     */
    (*ifInBroadcastPkts_val_ptr) = rowreq_ctx->data.ifInBroadcastPkts;

    return MFD_SUCCESS;
}                               /* ifInBroadcastPkts_get */

/*---------------------------------------------------------------------
 * IF-MIB::ifXEntry.ifOutMulticastPkts
 * ifOutMulticastPkts is subid 4 of ifXEntry.
 * Its status is Current, and its access level is ReadOnly.
 * OID: .1.3.6.1.2.1.31.1.1.1.4
 * Description:
The total number of packets that higher-level protocols
            requested be transmitted, and which were addressed to a
            multicast address at this sub-layer, including those that
            were discarded or not sent.  For a MAC layer protocol, this
            includes both Group and Functional addresses.

            Discontinuities in the value of this counter can occur at
            re-initialization of the management system, and at other
            times as indicated by the value of
            ifCounterDiscontinuityTime.
 *
 * Attributes:
 *   accessible 1     isscalar 0     enums  0      hasdefval 0
 *   readable   1     iscolumn 1     ranges 0      hashint   0
 *   settable   0
 *
 *
 * Its syntax is COUNTER (based on perltype COUNTER)
 * The net-snmp type is ASN_COUNTER. The C type decl is u_long (u_long)
 */
/**
 * Extract the current value of the ifOutMulticastPkts data.
 *
 * Set a value using the data context for the row.
 *
 * @param rowreq_ctx
 *        Pointer to the row request context.
 * @param ifOutMulticastPkts_val_ptr
 *        Pointer to storage for a u_long variable
 *
 * @retval MFD_SUCCESS         : success
 * @retval MFD_SKIP            : skip this node (no value for now)
 * @retval MFD_ERROR           : Any other error
 */
int
ifOutMulticastPkts_get(ifXTable_rowreq_ctx * rowreq_ctx,
                       u_long * ifOutMulticastPkts_val_ptr)
{
   /** we should have a non-NULL pointer */
    netsnmp_assert(NULL != ifOutMulticastPkts_val_ptr);


    DEBUGMSGTL(("verbose:ifXTable:ifOutMulticastPkts_get", "called\n"));

    netsnmp_assert(NULL != rowreq_ctx);

    /*
     * TODO:231:o: |-> Extract the current value of the ifOutMulticastPkts data.
     * copy (* ifOutMulticastPkts_val_ptr ) from rowreq_ctx->data
     */
    (*ifOutMulticastPkts_val_ptr) = rowreq_ctx->data.ifOutMulticastPkts;

    return MFD_SUCCESS;
}                               /* ifOutMulticastPkts_get */

/*---------------------------------------------------------------------
 * IF-MIB::ifXEntry.ifOutBroadcastPkts
 * ifOutBroadcastPkts is subid 5 of ifXEntry.
 * Its status is Current, and its access level is ReadOnly.
 * OID: .1.3.6.1.2.1.31.1.1.1.5
 * Description:
The total number of packets that higher-level protocols
            requested be transmitted, and which were addressed to a
            broadcast address at this sub-layer, including those that
            were discarded or not sent.

            Discontinuities in the value of this counter can occur at
            re-initialization of the management system, and at other

            times as indicated by the value of
            ifCounterDiscontinuityTime.
 *
 * Attributes:
 *   accessible 1     isscalar 0     enums  0      hasdefval 0
 *   readable   1     iscolumn 1     ranges 0      hashint   0
 *   settable   0
 *
 *
 * Its syntax is COUNTER (based on perltype COUNTER)
 * The net-snmp type is ASN_COUNTER. The C type decl is u_long (u_long)
 */
/**
 * Extract the current value of the ifOutBroadcastPkts data.
 *
 * Set a value using the data context for the row.
 *
 * @param rowreq_ctx
 *        Pointer to the row request context.
 * @param ifOutBroadcastPkts_val_ptr
 *        Pointer to storage for a u_long variable
 *
 * @retval MFD_SUCCESS         : success
 * @retval MFD_SKIP            : skip this node (no value for now)
 * @retval MFD_ERROR           : Any other error
 */
int
ifOutBroadcastPkts_get(ifXTable_rowreq_ctx * rowreq_ctx,
                       u_long * ifOutBroadcastPkts_val_ptr)
{
   /** we should have a non-NULL pointer */
    netsnmp_assert(NULL != ifOutBroadcastPkts_val_ptr);


    DEBUGMSGTL(("verbose:ifXTable:ifOutBroadcastPkts_get", "called\n"));

    netsnmp_assert(NULL != rowreq_ctx);

    /*
     * TODO:231:o: |-> Extract the current value of the ifOutBroadcastPkts data.
     * copy (* ifOutBroadcastPkts_val_ptr ) from rowreq_ctx->data
     */
    (*ifOutBroadcastPkts_val_ptr) = rowreq_ctx->data.ifOutBroadcastPkts;

    return MFD_SUCCESS;
}                               /* ifOutBroadcastPkts_get */

/*---------------------------------------------------------------------
 * IF-MIB::ifXEntry.ifHCInOctets
 * ifHCInOctets is subid 6 of ifXEntry.
 * Its status is Current, and its access level is ReadOnly.
 * OID: .1.3.6.1.2.1.31.1.1.1.6
 * Description:
The total number of octets received on the interface,
            including framing characters.  This object is a 64-bit
            version of ifInOctets.

            Discontinuities in the value of this counter can occur at
            re-initialization of the management system, and at other
            times as indicated by the value of
            ifCounterDiscontinuityTime.
 *
 * Attributes:
 *   accessible 1     isscalar 0     enums  0      hasdefval 0
 *   readable   1     iscolumn 1     ranges 0      hashint   0
 *   settable   0
 *
 *
 * Its syntax is COUNTER64 (based on perltype COUNTER64)
 * The net-snmp type is ASN_COUNTER64. The C type decl is U64 (U64)
 */
/**
 * Extract the current value of the ifHCInOctets data.
 *
 * Set a value using the data context for the row.
 *
 * @param rowreq_ctx
 *        Pointer to the row request context.
 * @param ifHCInOctets_val_ptr
 *        Pointer to storage for a U64 variable
 *
 * @retval MFD_SUCCESS         : success
 * @retval MFD_SKIP            : skip this node (no value for now)
 * @retval MFD_ERROR           : Any other error
 */
int
ifHCInOctets_get(ifXTable_rowreq_ctx * rowreq_ctx,
                 U64 * ifHCInOctets_val_ptr)
{
   /** we should have a non-NULL pointer */
    netsnmp_assert(NULL != ifHCInOctets_val_ptr);

    /*
     * TODO:231:o: |-> copy ifHCInOctets data.
     * get (* ifHCInOctets_val_ptr ).low and (* ifHCInOctets_val_ptr ).high from rowreq_ctx->data
     */
    (*ifHCInOctets_val_ptr).high = rowreq_ctx->data.ifHCInOctets.high;
    (*ifHCInOctets_val_ptr).low = rowreq_ctx->data.ifHCInOctets.low;


    return MFD_SUCCESS;
}                               /* ifHCInOctets_get */

/*---------------------------------------------------------------------
 * IF-MIB::ifXEntry.ifHCInUcastPkts
 * ifHCInUcastPkts is subid 7 of ifXEntry.
 * Its status is Current, and its access level is ReadOnly.
 * OID: .1.3.6.1.2.1.31.1.1.1.7
 * Description:
The number of packets, delivered by this sub-layer to a
            higher (sub-)layer, which were not addressed to a multicast
            or broadcast address at this sub-layer.  This object is a
            64-bit version of ifInUcastPkts.

            Discontinuities in the value of this counter can occur at
            re-initialization of the management system, and at other
            times as indicated by the value of
            ifCounterDiscontinuityTime.
 *
 * Attributes:
 *   accessible 1     isscalar 0     enums  0      hasdefval 0
 *   readable   1     iscolumn 1     ranges 0      hashint   0
 *   settable   0
 *
 *
 * Its syntax is COUNTER64 (based on perltype COUNTER64)
 * The net-snmp type is ASN_COUNTER64. The C type decl is U64 (U64)
 */
/**
 * Extract the current value of the ifHCInUcastPkts data.
 *
 * Set a value using the data context for the row.
 *
 * @param rowreq_ctx
 *        Pointer to the row request context.
 * @param ifHCInUcastPkts_val_ptr
 *        Pointer to storage for a U64 variable
 *
 * @retval MFD_SUCCESS         : success
 * @retval MFD_SKIP            : skip this node (no value for now)
 * @retval MFD_ERROR           : Any other error
 */
int
ifHCInUcastPkts_get(ifXTable_rowreq_ctx * rowreq_ctx,
                    U64 * ifHCInUcastPkts_val_ptr)
{
   /** we should have a non-NULL pointer */
    netsnmp_assert(NULL != ifHCInUcastPkts_val_ptr);

    /*
     * TODO:231:o: |-> copy ifHCInUcastPkts data.
     * get (* ifHCInUcastPkts_val_ptr ).low and (* ifHCInUcastPkts_val_ptr ).high from rowreq_ctx->data
     */
    (*ifHCInUcastPkts_val_ptr).high =
        rowreq_ctx->data.ifHCInUcastPkts.high;
    (*ifHCInUcastPkts_val_ptr).low = rowreq_ctx->data.ifHCInUcastPkts.low;


    return MFD_SUCCESS;
}                               /* ifHCInUcastPkts_get */

/*---------------------------------------------------------------------
 * IF-MIB::ifXEntry.ifHCInMulticastPkts
 * ifHCInMulticastPkts is subid 8 of ifXEntry.
 * Its status is Current, and its access level is ReadOnly.
 * OID: .1.3.6.1.2.1.31.1.1.1.8
 * Description:
The number of packets, delivered by this sub-layer to a
            higher (sub-)layer, which were addressed to a multicast
            address at this sub-layer.  For a MAC layer protocol, this
            includes both Group and Functional addresses.  This object
            is a 64-bit version of ifInMulticastPkts.

            Discontinuities in the value of this counter can occur at
            re-initialization of the management system, and at other
            times as indicated by the value of
            ifCounterDiscontinuityTime.
 *
 * Attributes:
 *   accessible 1     isscalar 0     enums  0      hasdefval 0
 *   readable   1     iscolumn 1     ranges 0      hashint   0
 *   settable   0
 *
 *
 * Its syntax is COUNTER64 (based on perltype COUNTER64)
 * The net-snmp type is ASN_COUNTER64. The C type decl is U64 (U64)
 */
/**
 * Extract the current value of the ifHCInMulticastPkts data.
 *
 * Set a value using the data context for the row.
 *
 * @param rowreq_ctx
 *        Pointer to the row request context.
 * @param ifHCInMulticastPkts_val_ptr
 *        Pointer to storage for a U64 variable
 *
 * @retval MFD_SUCCESS         : success
 * @retval MFD_SKIP            : skip this node (no value for now)
 * @retval MFD_ERROR           : Any other error
 */
int
ifHCInMulticastPkts_get(ifXTable_rowreq_ctx * rowreq_ctx,
                        U64 * ifHCInMulticastPkts_val_ptr)
{
   /** we should have a non-NULL pointer */
    netsnmp_assert(NULL != ifHCInMulticastPkts_val_ptr);

    /*
     * TODO:231:o: |-> copy ifHCInMulticastPkts data.
     * get (* ifHCInMulticastPkts_val_ptr ).low and (* ifHCInMulticastPkts_val_ptr ).high from rowreq_ctx->data
     */
    (*ifHCInMulticastPkts_val_ptr).high =
        rowreq_ctx->data.ifHCInMulticastPkts.high;
    (*ifHCInMulticastPkts_val_ptr).low =
        rowreq_ctx->data.ifHCInMulticastPkts.low;


    return MFD_SUCCESS;
}                               /* ifHCInMulticastPkts_get */

/*---------------------------------------------------------------------
 * IF-MIB::ifXEntry.ifHCInBroadcastPkts
 * ifHCInBroadcastPkts is subid 9 of ifXEntry.
 * Its status is Current, and its access level is ReadOnly.
 * OID: .1.3.6.1.2.1.31.1.1.1.9
 * Description:
The number of packets, delivered by this sub-layer to a
            higher (sub-)layer, which were addressed to a broadcast
            address at this sub-layer.  This object is a 64-bit version
            of ifInBroadcastPkts.

            Discontinuities in the value of this counter can occur at
            re-initialization of the management system, and at other
            times as indicated by the value of
            ifCounterDiscontinuityTime.
 *
 * Attributes:
 *   accessible 1     isscalar 0     enums  0      hasdefval 0
 *   readable   1     iscolumn 1     ranges 0      hashint   0
 *   settable   0
 *
 *
 * Its syntax is COUNTER64 (based on perltype COUNTER64)
 * The net-snmp type is ASN_COUNTER64. The C type decl is U64 (U64)
 */
/**
 * Extract the current value of the ifHCInBroadcastPkts data.
 *
 * Set a value using the data context for the row.
 *
 * @param rowreq_ctx
 *        Pointer to the row request context.
 * @param ifHCInBroadcastPkts_val_ptr
 *        Pointer to storage for a U64 variable
 *
 * @retval MFD_SUCCESS         : success
 * @retval MFD_SKIP            : skip this node (no value for now)
 * @retval MFD_ERROR           : Any other error
 */
int
ifHCInBroadcastPkts_get(ifXTable_rowreq_ctx * rowreq_ctx,
                        U64 * ifHCInBroadcastPkts_val_ptr)
{
   /** we should have a non-NULL pointer */
    netsnmp_assert(NULL != ifHCInBroadcastPkts_val_ptr);

    /*
     * TODO:231:o: |-> copy ifHCInBroadcastPkts data.
     * get (* ifHCInBroadcastPkts_val_ptr ).low and (* ifHCInBroadcastPkts_val_ptr ).high from rowreq_ctx->data
     */
    (*ifHCInBroadcastPkts_val_ptr).high =
        rowreq_ctx->data.ifHCInBroadcastPkts.high;
    (*ifHCInBroadcastPkts_val_ptr).low =
        rowreq_ctx->data.ifHCInBroadcastPkts.low;


    return MFD_SUCCESS;
}                               /* ifHCInBroadcastPkts_get */

/*---------------------------------------------------------------------
 * IF-MIB::ifXEntry.ifHCOutOctets
 * ifHCOutOctets is subid 10 of ifXEntry.
 * Its status is Current, and its access level is ReadOnly.
 * OID: .1.3.6.1.2.1.31.1.1.1.10
 * Description:
The total number of octets transmitted out of the
            interface, including framing characters.  This object is a
            64-bit version of ifOutOctets.

            Discontinuities in the value of this counter can occur at
            re-initialization of the management system, and at other
            times as indicated by the value of
            ifCounterDiscontinuityTime.
 *
 * Attributes:
 *   accessible 1     isscalar 0     enums  0      hasdefval 0
 *   readable   1     iscolumn 1     ranges 0      hashint   0
 *   settable   0
 *
 *
 * Its syntax is COUNTER64 (based on perltype COUNTER64)
 * The net-snmp type is ASN_COUNTER64. The C type decl is U64 (U64)
 */
/**
 * Extract the current value of the ifHCOutOctets data.
 *
 * Set a value using the data context for the row.
 *
 * @param rowreq_ctx
 *        Pointer to the row request context.
 * @param ifHCOutOctets_val_ptr
 *        Pointer to storage for a U64 variable
 *
 * @retval MFD_SUCCESS         : success
 * @retval MFD_SKIP            : skip this node (no value for now)
 * @retval MFD_ERROR           : Any other error
 */
int
ifHCOutOctets_get(ifXTable_rowreq_ctx * rowreq_ctx,
                  U64 * ifHCOutOctets_val_ptr)
{
   /** we should have a non-NULL pointer */
    netsnmp_assert(NULL != ifHCOutOctets_val_ptr);

    /*
     * TODO:231:o: |-> copy ifHCOutOctets data.
     * get (* ifHCOutOctets_val_ptr ).low and (* ifHCOutOctets_val_ptr ).high from rowreq_ctx->data
     */
    (*ifHCOutOctets_val_ptr).high = rowreq_ctx->data.ifHCOutOctets.high;
    (*ifHCOutOctets_val_ptr).low = rowreq_ctx->data.ifHCOutOctets.low;


    return MFD_SUCCESS;
}                               /* ifHCOutOctets_get */

/*---------------------------------------------------------------------
 * IF-MIB::ifXEntry.ifHCOutUcastPkts
 * ifHCOutUcastPkts is subid 11 of ifXEntry.
 * Its status is Current, and its access level is ReadOnly.
 * OID: .1.3.6.1.2.1.31.1.1.1.11
 * Description:
The total number of packets that higher-level protocols
            requested be transmitted, and which were not addressed to a
            multicast or broadcast address at this sub-layer, including
            those that were discarded or not sent.  This object is a
            64-bit version of ifOutUcastPkts.

            Discontinuities in the value of this counter can occur at
            re-initialization of the management system, and at other
            times as indicated by the value of
            ifCounterDiscontinuityTime.
 *
 * Attributes:
 *   accessible 1     isscalar 0     enums  0      hasdefval 0
 *   readable   1     iscolumn 1     ranges 0      hashint   0
 *   settable   0
 *
 *
 * Its syntax is COUNTER64 (based on perltype COUNTER64)
 * The net-snmp type is ASN_COUNTER64. The C type decl is U64 (U64)
 */
/**
 * Extract the current value of the ifHCOutUcastPkts data.
 *
 * Set a value using the data context for the row.
 *
 * @param rowreq_ctx
 *        Pointer to the row request context.
 * @param ifHCOutUcastPkts_val_ptr
 *        Pointer to storage for a U64 variable
 *
 * @retval MFD_SUCCESS         : success
 * @retval MFD_SKIP            : skip this node (no value for now)
 * @retval MFD_ERROR           : Any other error
 */
int
ifHCOutUcastPkts_get(ifXTable_rowreq_ctx * rowreq_ctx,
                     U64 * ifHCOutUcastPkts_val_ptr)
{
   /** we should have a non-NULL pointer */
    netsnmp_assert(NULL != ifHCOutUcastPkts_val_ptr);

    /*
     * TODO:231:o: |-> copy ifHCOutUcastPkts data.
     * get (* ifHCOutUcastPkts_val_ptr ).low and (* ifHCOutUcastPkts_val_ptr ).high from rowreq_ctx->data
     */
    (*ifHCOutUcastPkts_val_ptr).high =
        rowreq_ctx->data.ifHCOutUcastPkts.high;
    (*ifHCOutUcastPkts_val_ptr).low =
        rowreq_ctx->data.ifHCOutUcastPkts.low;


    return MFD_SUCCESS;
}                               /* ifHCOutUcastPkts_get */

/*---------------------------------------------------------------------
 * IF-MIB::ifXEntry.ifHCOutMulticastPkts
 * ifHCOutMulticastPkts is subid 12 of ifXEntry.
 * Its status is Current, and its access level is ReadOnly.
 * OID: .1.3.6.1.2.1.31.1.1.1.12
 * Description:
The total number of packets that higher-level protocols
            requested be transmitted, and which were addressed to a
            multicast address at this sub-layer, including those that
            were discarded or not sent.  For a MAC layer protocol, this
            includes both Group and Functional addresses.  This object
            is a 64-bit version of ifOutMulticastPkts.

            Discontinuities in the value of this counter can occur at
            re-initialization of the management system, and at other
            times as indicated by the value of
            ifCounterDiscontinuityTime.
 *
 * Attributes:
 *   accessible 1     isscalar 0     enums  0      hasdefval 0
 *   readable   1     iscolumn 1     ranges 0      hashint   0
 *   settable   0
 *
 *
 * Its syntax is COUNTER64 (based on perltype COUNTER64)
 * The net-snmp type is ASN_COUNTER64. The C type decl is U64 (U64)
 */
/**
 * Extract the current value of the ifHCOutMulticastPkts data.
 *
 * Set a value using the data context for the row.
 *
 * @param rowreq_ctx
 *        Pointer to the row request context.
 * @param ifHCOutMulticastPkts_val_ptr
 *        Pointer to storage for a U64 variable
 *
 * @retval MFD_SUCCESS         : success
 * @retval MFD_SKIP            : skip this node (no value for now)
 * @retval MFD_ERROR           : Any other error
 */
int
ifHCOutMulticastPkts_get(ifXTable_rowreq_ctx * rowreq_ctx,
                         U64 * ifHCOutMulticastPkts_val_ptr)
{
   /** we should have a non-NULL pointer */
    netsnmp_assert(NULL != ifHCOutMulticastPkts_val_ptr);

    /*
     * TODO:231:o: |-> copy ifHCOutMulticastPkts data.
     * get (* ifHCOutMulticastPkts_val_ptr ).low and (* ifHCOutMulticastPkts_val_ptr ).high from rowreq_ctx->data
     */
    (*ifHCOutMulticastPkts_val_ptr).high =
        rowreq_ctx->data.ifHCOutMulticastPkts.high;
    (*ifHCOutMulticastPkts_val_ptr).low =
        rowreq_ctx->data.ifHCOutMulticastPkts.low;


    return MFD_SUCCESS;
}                               /* ifHCOutMulticastPkts_get */

/*---------------------------------------------------------------------
 * IF-MIB::ifXEntry.ifHCOutBroadcastPkts
 * ifHCOutBroadcastPkts is subid 13 of ifXEntry.
 * Its status is Current, and its access level is ReadOnly.
 * OID: .1.3.6.1.2.1.31.1.1.1.13
 * Description:
The total number of packets that higher-level protocols
            requested be transmitted, and which were addressed to a
            broadcast address at this sub-layer, including those that
            were discarded or not sent.  This object is a 64-bit version
            of ifOutBroadcastPkts.

            Discontinuities in the value of this counter can occur at
            re-initialization of the management system, and at other
            times as indicated by the value of
            ifCounterDiscontinuityTime.
 *
 * Attributes:
 *   accessible 1     isscalar 0     enums  0      hasdefval 0
 *   readable   1     iscolumn 1     ranges 0      hashint   0
 *   settable   0
 *
 *
 * Its syntax is COUNTER64 (based on perltype COUNTER64)
 * The net-snmp type is ASN_COUNTER64. The C type decl is U64 (U64)
 */
/**
 * Extract the current value of the ifHCOutBroadcastPkts data.
 *
 * Set a value using the data context for the row.
 *
 * @param rowreq_ctx
 *        Pointer to the row request context.
 * @param ifHCOutBroadcastPkts_val_ptr
 *        Pointer to storage for a U64 variable
 *
 * @retval MFD_SUCCESS         : success
 * @retval MFD_SKIP            : skip this node (no value for now)
 * @retval MFD_ERROR           : Any other error
 */
int
ifHCOutBroadcastPkts_get(ifXTable_rowreq_ctx * rowreq_ctx,
                         U64 * ifHCOutBroadcastPkts_val_ptr)
{
   /** we should have a non-NULL pointer */
    netsnmp_assert(NULL != ifHCOutBroadcastPkts_val_ptr);

    /*
     * TODO:231:o: |-> copy ifHCOutBroadcastPkts data.
     * get (* ifHCOutBroadcastPkts_val_ptr ).low and (* ifHCOutBroadcastPkts_val_ptr ).high from rowreq_ctx->data
     */
    (*ifHCOutBroadcastPkts_val_ptr).high =
        rowreq_ctx->data.ifHCOutBroadcastPkts.high;
    (*ifHCOutBroadcastPkts_val_ptr).low =
        rowreq_ctx->data.ifHCOutBroadcastPkts.low;


    return MFD_SUCCESS;
}                               /* ifHCOutBroadcastPkts_get */

/*---------------------------------------------------------------------
 * IF-MIB::ifXEntry.ifLinkUpDownTrapEnable
 * ifLinkUpDownTrapEnable is subid 14 of ifXEntry.
 * Its status is Current, and its access level is ReadWrite.
 * OID: .1.3.6.1.2.1.31.1.1.1.14
 * Description:
Indicates whether linkUp/linkDown traps should be generated
            for this interface.

            By default, this object should have the value enabled(1) for
            interfaces which do not operate on 'top' of any other
            interface (as defined in the ifStackTable), and disabled(2)
            otherwise.
 *
 * Attributes:
 *   accessible 1     isscalar 0     enums  1      hasdefval 0
 *   readable   1     iscolumn 1     ranges 0      hashint   0
 *   settable   1
 *
 * Enum range: 2/8. Values:  enabled(1), disabled(2)
 *
 * Its syntax is INTEGER (based on perltype INTEGER)
 * The net-snmp type is ASN_INTEGER. The C type decl is long (u_long)
 */
/**
 * Extract the current value of the ifLinkUpDownTrapEnable data.
 *
 * Set a value using the data context for the row.
 *
 * @param rowreq_ctx
 *        Pointer to the row request context.
 * @param ifLinkUpDownTrapEnable_val_ptr
 *        Pointer to storage for a long variable
 *
 * @retval MFD_SUCCESS         : success
 * @retval MFD_SKIP            : skip this node (no value for now)
 * @retval MFD_ERROR           : Any other error
 */
int
ifLinkUpDownTrapEnable_get(ifXTable_rowreq_ctx * rowreq_ctx,
                           u_long * ifLinkUpDownTrapEnable_val_ptr)
{
   /** we should have a non-NULL pointer */
    netsnmp_assert(NULL != ifLinkUpDownTrapEnable_val_ptr);


    DEBUGMSGTL(("verbose:ifXTable:ifLinkUpDownTrapEnable_get",
                "called\n"));

    netsnmp_assert(NULL != rowreq_ctx);

    if (0 == rowreq_ctx->data.ifLinkUpDownTrapEnable)
        return MFD_SKIP;

    /*
     * TODO:231:o: |-> Extract the current value of the ifLinkUpDownTrapEnable data.
     * copy (* ifLinkUpDownTrapEnable_val_ptr ) from rowreq_ctx->data
     */
    (*ifLinkUpDownTrapEnable_val_ptr) =
        rowreq_ctx->data.ifLinkUpDownTrapEnable;

    return MFD_SUCCESS;
}                               /* ifLinkUpDownTrapEnable_get */

/*---------------------------------------------------------------------
 * IF-MIB::ifXEntry.ifHighSpeed
 * ifHighSpeed is subid 15 of ifXEntry.
 * Its status is Current, and its access level is ReadOnly.
 * OID: .1.3.6.1.2.1.31.1.1.1.15
 * Description:
An estimate of the interface's current bandwidth in units
            of 1,000,000 bits per second.  If this object reports a
            value of `n' then the speed of the interface is somewhere in
            the range of `n-500,000' to `n+499,999'.  For interfaces
            which do not vary in bandwidth or for those where no
            accurate estimation can be made, this object should contain
            the nominal bandwidth.  For a sub-layer which has no concept
            of bandwidth, this object should be zero.
 *
 * Attributes:
 *   accessible 1     isscalar 0     enums  0      hasdefval 0
 *   readable   1     iscolumn 1     ranges 0      hashint   0
 *   settable   0
 *
 *
 * Its syntax is GAUGE (based on perltype GAUGE)
 * The net-snmp type is ASN_GAUGE. The C type decl is u_long (u_long)
 */
/**
 * Extract the current value of the ifHighSpeed data.
 *
 * Set a value using the data context for the row.
 *
 * @param rowreq_ctx
 *        Pointer to the row request context.
 * @param ifHighSpeed_val_ptr
 *        Pointer to storage for a u_long variable
 *
 * @retval MFD_SUCCESS         : success
 * @retval MFD_SKIP            : skip this node (no value for now)
 * @retval MFD_ERROR           : Any other error
 */
int
ifHighSpeed_get(ifXTable_rowreq_ctx * rowreq_ctx,
                u_long * ifHighSpeed_val_ptr)
{
   /** we should have a non-NULL pointer */
    netsnmp_assert(NULL != ifHighSpeed_val_ptr);


    DEBUGMSGTL(("verbose:ifXTable:ifHighSpeed_get", "called\n"));

    netsnmp_assert(NULL != rowreq_ctx);

    /*
     * TODO:231:o: |-> Extract the current value of the ifHighSpeed data.
     * copy (* ifHighSpeed_val_ptr ) from rowreq_ctx->data
     */
    if (0 == rowreq_ctx->data.ifHighSpeed)
        (*ifHighSpeed_val_ptr) = rowreq_ctx->data.ifSpeed / 1000000;
    else
        (*ifHighSpeed_val_ptr) = rowreq_ctx->data.ifHighSpeed;

    return MFD_SUCCESS;
}                               /* ifHighSpeed_get */

/*---------------------------------------------------------------------
 * IF-MIB::ifXEntry.ifPromiscuousMode
 * ifPromiscuousMode is subid 16 of ifXEntry.
 * Its status is Current, and its access level is ReadWrite.
 * OID: .1.3.6.1.2.1.31.1.1.1.16
 * Description:
This object has a value of false(2) if this interface only
            accepts packets/frames that are addressed to this station.
            This object has a value of true(1) when the station accepts
            all packets/frames transmitted on the media.  The value
            true(1) is only legal on certain types of media.  If legal,
            setting this object to a value of true(1) may require the
            interface to be reset before becoming effective.

            The value of ifPromiscuousMode does not affect the reception
            of broadcast and multicast packets/frames by the interface.
 *
 * Attributes:
 *   accessible 1     isscalar 0     enums  1      hasdefval 0
 *   readable   1     iscolumn 1     ranges 0      hashint   0
 *   settable   1
 *
 * Enum range: 2/8. Values:  true(1), false(2)
 *
 * Its syntax is TruthValue (based on perltype INTEGER)
 * The net-snmp type is ASN_INTEGER. The C type decl is long (u_long)
 */
/**
 * Extract the current value of the ifPromiscuousMode data.
 *
 * Set a value using the data context for the row.
 *
 * @param rowreq_ctx
 *        Pointer to the row request context.
 * @param ifPromiscuousMode_val_ptr
 *        Pointer to storage for a long variable
 *
 * @retval MFD_SUCCESS         : success
 * @retval MFD_SKIP            : skip this node (no value for now)
 * @retval MFD_ERROR           : Any other error
 */
int
ifPromiscuousMode_get(ifXTable_rowreq_ctx * rowreq_ctx,
                      u_long * ifPromiscuousMode_val_ptr)
{
   /** we should have a non-NULL pointer */
    netsnmp_assert(NULL != ifPromiscuousMode_val_ptr);


    DEBUGMSGTL(("verbose:ifXTable:ifPromiscuousMode_get", "called\n"));

    netsnmp_assert(NULL != rowreq_ctx);

    /*
     * TODO:231:o: |-> Extract the current value of the ifPromiscuousMode data.
     * copy (* ifPromiscuousMode_val_ptr ) from rowreq_ctx->data
     */
    /** this is coming from the interface entry, which is a boolean */
    if (rowreq_ctx->data.ifPromiscuousMode)
        (*ifPromiscuousMode_val_ptr) = 1;
    else
        (*ifPromiscuousMode_val_ptr) = 2;

    return MFD_SUCCESS;
}                               /* ifPromiscuousMode_get */

/*---------------------------------------------------------------------
 * IF-MIB::ifXEntry.ifConnectorPresent
 * ifConnectorPresent is subid 17 of ifXEntry.
 * Its status is Current, and its access level is ReadOnly.
 * OID: .1.3.6.1.2.1.31.1.1.1.17
 * Description:
This object has the value 'true(1)' if the interface
            sublayer has a physical connector and the value 'false(2)'
            otherwise.
 *
 * Attributes:
 *   accessible 1     isscalar 0     enums  1      hasdefval 0
 *   readable   1     iscolumn 1     ranges 0      hashint   0
 *   settable   0
 *
 * Enum range: 2/8. Values:  true(1), false(2)
 *
 * Its syntax is TruthValue (based on perltype INTEGER)
 * The net-snmp type is ASN_INTEGER. The C type decl is long (u_long)
 */
/**
 * Extract the current value of the ifConnectorPresent data.
 *
 * Set a value using the data context for the row.
 *
 * @param rowreq_ctx
 *        Pointer to the row request context.
 * @param ifConnectorPresent_val_ptr
 *        Pointer to storage for a long variable
 *
 * @retval MFD_SUCCESS         : success
 * @retval MFD_SKIP            : skip this node (no value for now)
 * @retval MFD_ERROR           : Any other error
 */
int
ifConnectorPresent_get(ifXTable_rowreq_ctx * rowreq_ctx,
                       u_long * ifConnectorPresent_val_ptr)
{
   /** we should have a non-NULL pointer */
    netsnmp_assert(NULL != ifConnectorPresent_val_ptr);


    DEBUGMSGTL(("verbose:ifXTable:ifConnectorPresent_get", "called\n"));

    netsnmp_assert(NULL != rowreq_ctx);

    (*ifConnectorPresent_val_ptr) = rowreq_ctx->data.ifConnectorPresent ?
        TV_TRUE : TV_FALSE;

    return MFD_SUCCESS;
}                               /* ifConnectorPresent_get */

/*---------------------------------------------------------------------
 * IF-MIB::ifXEntry.ifAlias
 * ifAlias is subid 18 of ifXEntry.
 * Its status is Current, and its access level is ReadWrite.
 * OID: .1.3.6.1.2.1.31.1.1.1.18
 * Description:
This object is an 'alias' name for the interface as
            specified by a network manager, and provides a non-volatile
            'handle' for the interface.

            On the first instantiation of an interface, the value of
            ifAlias associated with that interface is the zero-length
            string.  As and when a value is written into an instance of
            ifAlias through a network management set operation, then the
            agent must retain the supplied value in the ifAlias instance
            associated with the same interface for as long as that
            interface remains instantiated, including across all re-
            initializations/reboots of the network management system,
            including those which result in a change of the interface's
            ifIndex value.

            An example of the value which a network manager might store
            in this object for a WAN interface is the (Telco's) circuit
            number/identifier of the interface.

            Some agents may support write-access only for interfaces
            having particular values of ifType.  An agent which supports
            write access to this object is required to keep the value in
            non-volatile storage, but it may limit the length of new
            values depending on how much storage is already occupied by
            the current values for other interfaces.
 *
 * Attributes:
 *   accessible 1     isscalar 0     enums  0      hasdefval 0
 *   readable   1     iscolumn 1     ranges 1      hashint   1
 *   settable   1
 *   hint: 255a
 *
 * Ranges:  0 - 64;
 *
 * Its syntax is DisplayString (based on perltype OCTETSTR)
 * The net-snmp type is ASN_OCTET_STR. The C type decl is char (char)
 * This data type requires a length.  (Max 64)
 */
/**
 * Extract the current value of the ifAlias data.
 *
 * Set a value using the data context for the row.
 *
 * @param rowreq_ctx
 *        Pointer to the row request context.
 * @param ifAlias_val_ptr_ptr
 *        Pointer to storage for a char variable
 * @param ifAlias_val_ptr_len_ptr
 *        Pointer to a size_t. On entry, it will contain the size (in bytes)
 *        pointed to by ifAlias.
 *        On exit, this value should contain the data size (in bytes).
 *
 * @retval MFD_SUCCESS         : success
 * @retval MFD_SKIP            : skip this node (no value for now)
 * @retval MFD_ERROR           : Any other error
*
 * @note If you need more than (*ifAlias_val_ptr_len_ptr) bytes of memory,
 *       allocate it using malloc() and update ifAlias_val_ptr_ptr.
 *       <b>DO NOT</b> free the previous pointer.
 *       The MFD helper will release the memory you allocate.
 *
 * @remark If you call this function yourself, you are responsible
 *         for checking if the pointer changed, and freeing any
 *         previously allocated memory. (Not necessary if you pass
 *         in a pointer to static memory, obviously.)
 */
int
ifAlias_get(ifXTable_rowreq_ctx * rowreq_ctx, char **ifAlias_val_ptr_ptr,
            size_t * ifAlias_val_ptr_len_ptr)
{
   /** we should have a non-NULL pointer and enough storage */
    netsnmp_assert((NULL != ifAlias_val_ptr_ptr)
                   && (NULL != *ifAlias_val_ptr_ptr));
    netsnmp_assert(NULL != ifAlias_val_ptr_len_ptr);


    DEBUGMSGTL(("verbose:ifXTable:ifAlias_get", "called\n"));

    netsnmp_assert(NULL != rowreq_ctx);

    /*
     * TODO:231:o: |-> Extract the current value of the ifAlias data.
     * copy (* ifAlias_val_ptr_ptr ) data and (* ifAlias_val_ptr_len_ptr ) from rowreq_ctx->data
     */
    /*
     * make sure there is enough space for ifAlias data
     */
    if ((NULL == (*ifAlias_val_ptr_ptr)) ||
        ((*ifAlias_val_ptr_len_ptr) <
         (rowreq_ctx->data.ifAlias_len *
          sizeof(rowreq_ctx->data.ifAlias[0])))) {
        /*
         * allocate space for ifAlias data
         */
        (*ifAlias_val_ptr_ptr) = (char*)
            malloc(rowreq_ctx->data.ifAlias_len *
                   sizeof(rowreq_ctx->data.ifAlias[0]));
        if (NULL == (*ifAlias_val_ptr_ptr)) {
            snmp_log(LOG_ERR, "could not allocate memory\n");
            return MFD_ERROR;
        }
    }
    (*ifAlias_val_ptr_len_ptr) =
        rowreq_ctx->data.ifAlias_len * sizeof(rowreq_ctx->data.ifAlias[0]);
    memcpy((*ifAlias_val_ptr_ptr), rowreq_ctx->data.ifAlias,
           rowreq_ctx->data.ifAlias_len *
           sizeof(rowreq_ctx->data.ifAlias[0]));

    return MFD_SUCCESS;
}                               /* ifAlias_get */

/*---------------------------------------------------------------------
 * IF-MIB::ifXEntry.ifCounterDiscontinuityTime
 * ifCounterDiscontinuityTime is subid 19 of ifXEntry.
 * Its status is Current, and its access level is ReadOnly.
 * OID: .1.3.6.1.2.1.31.1.1.1.19
 * Description:
The value of sysUpTime on the most recent occasion at which
            any one or more of this interface's counters suffered a
            discontinuity.  The relevant counters are the specific
            instances associated with this interface of any Counter32 or

            Counter64 object contained in the ifTable or ifXTable.  If
            no such discontinuities have occurred since the last re-
            initialization of the local management subsystem, then this
            object contains a zero value.
 *
 * Attributes:
 *   accessible 1     isscalar 0     enums  0      hasdefval 0
 *   readable   1     iscolumn 1     ranges 0      hashint   0
 *   settable   0
 *
 *
 * Its syntax is TimeStamp (based on perltype TICKS)
 * The net-snmp type is ASN_TIMETICKS. The C type decl is u_long (u_long)
 */
/**
 * Extract the current value of the ifCounterDiscontinuityTime data.
 *
 * Set a value using the data context for the row.
 *
 * @param rowreq_ctx
 *        Pointer to the row request context.
 * @param ifCounterDiscontinuityTime_val_ptr
 *        Pointer to storage for a u_long variable
 *
 * @retval MFD_SUCCESS         : success
 * @retval MFD_SKIP            : skip this node (no value for now)
 * @retval MFD_ERROR           : Any other error
 */
int
ifCounterDiscontinuityTime_get(ifXTable_rowreq_ctx * rowreq_ctx,
                               u_long * ifCounterDiscontinuityTime_val_ptr)
{
   /** we should have a non-NULL pointer */
    netsnmp_assert(NULL != ifCounterDiscontinuityTime_val_ptr);


    DEBUGMSGTL(("verbose:ifXTable:ifCounterDiscontinuityTime_get",
                "called\n"));

    netsnmp_assert(NULL != rowreq_ctx);

    /*
     * TODO:231:o: |-> Extract the current value of the ifCounterDiscontinuityTime data.
     * copy (* ifCounterDiscontinuityTime_val_ptr ) from rowreq_ctx->data
     */
    (*ifCounterDiscontinuityTime_val_ptr) =
        rowreq_ctx->data.ifCounterDiscontinuityTime;

    return MFD_SUCCESS;
}                               /* ifCounterDiscontinuityTime_get */



/** @} */
/**********************************************************************
 **********************************************************************
 ***
 *** Table ifXTable
 ***
 **********************************************************************
 **********************************************************************/
/*
 * IF-MIB::ifXTable is subid 1 of ifMIBObjects.
 * Its status is Current.
 * OID: .1.3.6.1.2.1.31.1.1, length: 9
 */
    /*
     * NOTE: if you update this chart, please update the versions in
     *       local/mib2c-conf.d/parent-set.m2i
     *       agent/mibgroup/helpers/baby_steps.c
     * while you're at it.
     */
    /*
     ***********************************************************************
     * Baby Steps Flow Chart (2004.06.05)                                  *
     *                                                                     *
     * +--------------+    +================+    U = unconditional path    *
     * |optional state|    ||required state||    S = path for success      *
     * +--------------+    +================+    E = path for error        *
     ***********************************************************************
     *
     *                        +--------------+
     *                        |     pre      |
     *                        |   request    |
     *                        +--------------+
     *                               | U
     *                        +==============+
     *       +----------------||  object    ||
     *       |              E ||  lookup    ||
     *       |                +==============+
     *       |                       | S
     *       |                +==============+
     *       |              E ||   check    ||
     *       |<---------------||   values   ||
     *       |                +==============+
     *       |                       | S
     *       |                +==============+
     *       |       +<-------||   undo     ||
     *       |       |      E ||   setup    ||
     *       |       |        +==============+
     *       |       |               | S
     *       |       |        +==============+
     *       |       |        ||    set     ||-------------------------->+
     *       |       |        ||   value    || E                         |
     *       |       |        +==============+                           |
     *       |       |               | S                                 |
     *       |       |        +--------------+                           |
     *       |       |        |    check     |-------------------------->|
     *       |       |        |  consistency | E                         |
     *       |       |        +--------------+                           |
     *       |       |               | S                                 |
     *       |       |        +==============+         +==============+  |
     *       |       |        ||   commit   ||-------->||     undo   ||  |
     *       |       |        ||            || E       ||    commit  ||  |
     *       |       |        +==============+         +==============+  |
     *       |       |               | S                     U |<--------+
     *       |       |        +--------------+         +==============+
     *       |       |        | irreversible |         ||    undo    ||
     *       |       |        |    commit    |         ||     set    ||
     *       |       |        +--------------+         +==============+
     *       |       |               | U                     U |
     *       |       +-------------->|<------------------------+
     *       |                +==============+
     *       |                ||   undo     ||
     *       |                ||  cleanup   ||
     *       |                +==============+
     *       +---------------------->| U
     *                        +--------------+
     *                        |    post      |
     *                        |   request    |
     *                        +--------------+
     *
     */

/**
 * Setup up context with information needed to undo a set request.
 *
 * This function will be called before the individual node undo setup
 * functions are called. If you need to do any undo setup that is not
 * related to a specific column, you can do it here.
 *
 * Note that the undo context has been allocated with
 * ifXTable_allocate_data(), but may need extra
 * initialization similar to what you may have done in
 * ifXTable_rowreq_ctx_init().
 * Note that an individual node's undo_setup function will only be called
 * if that node is being set to a new value.
 *
 * If there is any setup specific to a particular column (e.g. allocating
 * memory for a string), you should do that setup in the node's undo_setup
 * function, so it won't be done unless it is necessary.
 *
 * @param rowreq_ctx
 *        Pointer to the table context (ifXTable_rowreq_ctx)
 *
 * @retval MFD_SUCCESS : success
 * @retval MFD_ERROR   : error. set will fail.
 */
int
ifXTable_undo_setup(ifXTable_rowreq_ctx * rowreq_ctx)
{
    int             rc = MFD_SUCCESS;

    DEBUGMSGTL(("verbose:ifXTable:ifXTable_undo_setup", "called\n"));

    /** we should have a non-NULL pointer */
    netsnmp_assert(NULL != rowreq_ctx);

    /*
     * TODO:451:M: |-> Setup ifXTable undo.
     * set up ifXTable undo information, in preparation for a set.
     * Undo storage is in (* ifCounterDiscontinuityTime_val_ptr )*
     */

    return rc;
}                               /* ifXTable_undo_setup */

/**
 * Undo a set request.
 *
 * This function will be called before the individual node undo
 * functions are called. If you need to do any undo that is not
 * related to a specific column, you can do it here.
 *
 * Note that an individual node's undo function will only be called
 * if that node is being set to a new value.
 *
 * If there is anything  specific to a particular column (e.g. releasing
 * memory for a string), you should do that setup in the node's undo
 * function, so it won't be done unless it is necessary.
 *
 * @param rowreq_ctx
 *        Pointer to the table context (ifXTable_rowreq_ctx)
 *
 * @retval MFD_SUCCESS : success
 * @retval MFD_ERROR   : error. set will fail.
 */
int
ifXTable_undo(ifXTable_rowreq_ctx * rowreq_ctx)
{
    int             rc = MFD_SUCCESS;

    DEBUGMSGTL(("verbose:ifXTable:ifXTable_undo", "called\n"));

    /** we should have a non-NULL pointer */
    netsnmp_assert(NULL != rowreq_ctx);

    /*
     * TODO:451:M: |-> ifXTable undo.
     * ifXTable undo information, in response to a failed set.
     * Undo storage is in (* ifCounterDiscontinuityTime_val_ptr )*
     */

    return rc;
}                               /* ifXTable_undo_setup */

/**
 * Cleanup up context undo information.
 *
 * This function will be called after set/commit processing. If you
 * allocated any resources in undo_setup, this is the place to release
 * those resources.
 *
 * This function is called regardless of the success or failure of the set
 * request. If you need to perform different steps for cleanup depending
 * on success or failure, you can add a flag to the rowreq_ctx.
 *
 * @param rowreq_ctx
 *        Pointer to the table context (ifXTable_rowreq_ctx)
 *
 * @retval MFD_SUCCESS : success
 * @retval MFD_ERROR   : error
 */
int
ifXTable_undo_cleanup(ifXTable_rowreq_ctx * rowreq_ctx)
{
    int             rc = MFD_SUCCESS;

    DEBUGMSGTL(("verbose:ifXTable:ifXTable_undo_cleanup", "called\n"));

    /** we should have a non-NULL pointer */
    netsnmp_assert(NULL != rowreq_ctx);

    /*
     * TODO:452:M: |-> Cleanup ifXTable undo.
     * Undo storage is in (* ifCounterDiscontinuityTime_val_ptr )*
     */

    return rc;
}                               /* ifXTable_undo_cleanup */

/**
 * commit new values.
 *
 * At this point, you should have done everything you can to ensure that
 * this commit will not fail.
 *
 * Should you need different behavior depending on which columns were
 * set, rowreq_ctx->column_set_flags will indicate which writeable columns were
 * set. The definitions for the COLUMN_*_FLAG bits can be found in
 * ifXTable.h.
 * A new row will have the MFD_ROW_CREATED bit set in rowreq_flags.
 *
 * @param rowreq_ctx
 *        Pointer to the users context.
 *
 * @retval MFD_SUCCESS : success
 * @retval MFD_ERROR   : error
 */
int
ifXTable_commit(ifXTable_rowreq_ctx * rowreq_ctx)
{
    int             rc = MFD_SUCCESS;
    int             save_flags;

    DEBUGMSGTL(("verbose:ifXTable:ifXTable_commit", "called\n"));

    /** we should have a non-NULL pointer */
    netsnmp_assert(NULL != rowreq_ctx);

    /*
     * save flags, then clear until we actually do something
     */
    save_flags = rowreq_ctx->column_set_flags;
    rowreq_ctx->column_set_flags = 0;

    /*
     * commit ifXTable data
     * 1) check the column's flag in save_flags to see if it was set.
     * 2) clear the flag when you handle that column
     * 3) set the column's flag in column_set_flags if it needs undo
     *    processing in case of a failure.
     *
     * this is where one would usually commit data. In this case,
     * ifLinkUpDownTrapEnable and ifAlias are purely internal, so
     * nothing needs to be done. That leaves ifPromiscuosMode,
     * which I'm leery about implementing. Thus, at this point,
     * there is nothing to do except twiddle flag bits.
     */
    if (save_flags & COLUMN_IFLINKUPDOWNTRAPENABLE_FLAG) {
        save_flags &= ~COLUMN_IFLINKUPDOWNTRAPENABLE_FLAG;      /* clear ifLinkUpDownTrapEnable */
        /*
         * TODO:482:o: |-> commit column ifLinkUpDownTrapEnable.
         */
        /*
         * set flag, in case we need to undo ifLinkUpDownTrapEnable
         */
        rowreq_ctx->column_set_flags |= COLUMN_IFLINKUPDOWNTRAPENABLE_FLAG;
    }
#ifdef NETSNMP_ENABLE_PROMISCUOUSMODE_SET
    if (save_flags & COLUMN_IFPROMISCUOUSMODE_FLAG) {
        save_flags &= ~COLUMN_IFPROMISCUOUSMODE_FLAG;   /* clear ifPromiscuousMode */
        /*
         * TODO:482:o: |-> commit column ifPromiscuousMode.
         */
        rc = -1;
        if (-1 == rc) {
            snmp_log(LOG_ERR,
                     "ifXTable column ifPromiscuousMode commit failed\n");
        } else {
            /*
             * set flag, in case we need to undo ifPromiscuousMode
             */
            rowreq_ctx->column_set_flags |= COLUMN_IFPROMISCUOUSMODE_FLAG;
        }
    }
#endif                          /* NETSNMP_ENABLE_PROMISCUOUSMODE_SET */

    if (save_flags & COLUMN_IFALIAS_FLAG) {
        save_flags &= ~COLUMN_IFALIAS_FLAG;     /* clear ifAlias */
        /*
         * set flag, in case we need to undo ifAlias
         */
        rowreq_ctx->column_set_flags |= COLUMN_IFALIAS_FLAG;
    }

    /*
     * if we successfully commited this row, set the dirty flag.
     */
    if (MFD_SUCCESS == rc) {
        rowreq_ctx->rowreq_flags |= MFD_ROW_DIRTY;
    }

    if (save_flags) {
        snmp_log(LOG_ERR, "unhandled columns (0x%x) in commit\n",
                 save_flags);
        return MFD_ERROR;
    }

    return rc;
}                               /* ifXTable_commit */

/**
 * undo commit new values.
 *
 * Should you need different behavior depending on which columns were
 * set, rowreq_ctx->column_set_flags will indicate which writeable columns were
 * set. The definitions for the COLUMN_*_FLAG bits can be found in
 * ifXTable.h.
 * A new row will have the MFD_ROW_CREATED bit set in rowreq_flags.
 *
 * @param rowreq_ctx
 *        Pointer to the users context.
 *
 * @retval MFD_SUCCESS : success
 * @retval MFD_ERROR   : error
 */
int
ifXTable_undo_commit(ifXTable_rowreq_ctx * rowreq_ctx)
{
    int             rc = MFD_SUCCESS;

    DEBUGMSGTL(("verbose:ifXTable:ifXTable_undo_commit", "called\n"));

    /** we should have a non-NULL pointer */
    netsnmp_assert(NULL != rowreq_ctx);

    /*
     * TODO:485:M: |-> Undo ifXTable commit.
     * check the column's flag in rowreq_ctx->column_set_flags to see
     * if it was set during commit, then undo it.
     *
     * eg: if (rowreq_ctx->column_set_flags & COLUMN__FLAG) {}
     */


    /*
     * if we successfully un-commited this row, clear the dirty flag.
     */
    if (MFD_SUCCESS == rc) {
        rowreq_ctx->rowreq_flags &= ~MFD_ROW_DIRTY;
    }

    return rc;
}                               /* ifXTable_undo_commit */

/*
 * TODO:440:M: Implement ifXTable node value checks.
 * TODO:450:M: Implement ifXTable undo functions.
 * TODO:460:M: Implement ifXTable set functions.
 * TODO:480:M: Implement ifXTable commit functions.
 */
/*---------------------------------------------------------------------
 * IF-MIB::ifXEntry.ifLinkUpDownTrapEnable
 * ifLinkUpDownTrapEnable is subid 14 of ifXEntry.
 * Its status is Current, and its access level is ReadWrite.
 * OID: .1.3.6.1.2.1.31.1.1.1.14
 * Description:
Indicates whether linkUp/linkDown traps should be generated
            for this interface.

            By default, this object should have the value enabled(1) for
            interfaces which do not operate on 'top' of any other
            interface (as defined in the ifStackTable), and disabled(2)
            otherwise.
 *
 * Attributes:
 *   accessible 1     isscalar 0     enums  1      hasdefval 0
 *   readable   1     iscolumn 1     ranges 0      hashint   0
 *   settable   1
 *
 * Enum range: 2/8. Values:  enabled(1), disabled(2)
 *
 * Its syntax is INTEGER (based on perltype INTEGER)
 * The net-snmp type is ASN_INTEGER. The C type decl is long (u_long)
 */
/**
 * Check that the proposed new value is potentially valid.
 *
 * @param rowreq_ctx
 *        Pointer to the row request context.
 * @param ifLinkUpDownTrapEnable_val
 *        A long containing the new value.
 *
 * @retval MFD_SUCCESS        : incoming value is legal
 * @retval MFD_NOT_VALID_NOW  : incoming value is not valid now
 * @retval MFD_NOT_VALID_EVER : incoming value is never valid
 *
 * This is the place to check for requirements that are not
 * expressed in the mib syntax (for example, a requirement that
 * is detailed in the description for an object).
 *
 * You should check that the requested change between the undo value and the
 * new value is legal (ie, the transistion from one value to another
 * is legal).
 *      
 *@note
 * This check is only to determine if the new value
 * is \b potentially valid. This is the first check of many, and
 * is one of the simplest ones.
 * 
 *@note
 * this is not the place to do any checks for values
 * which depend on some other value in the mib. Those
 * types of checks should be done in the
 * ifXTable_check_dependencies() function.
 *
 * The following checks have already been done for you:
 *    The syntax is ASN_INTEGER
 *    The value is one of  enabled(1), disabled(2)
 *
 * If there a no other checks you need to do, simply return MFD_SUCCESS.
 *
 */
int
ifLinkUpDownTrapEnable_check_value(ifXTable_rowreq_ctx * rowreq_ctx,
                                   u_long ifLinkUpDownTrapEnable_val)
{
    DEBUGMSGTL(("verbose:ifXTable:ifLinkUpDownTrapEnable_check_value",
                "called\n"));

    /** should never get a NULL pointer */
    netsnmp_assert(NULL != rowreq_ctx);

    /*
     * TODO:441:o: |-> Check for valid ifLinkUpDownTrapEnable value.
     */

    return MFD_SUCCESS;         /* ifLinkUpDownTrapEnable value not illegal */
}                               /* ifLinkUpDownTrapEnable_check_value */

/**
 * Save old value information
 *
 * @param rowreq_ctx
 *        Pointer to the table context (ifXTable_rowreq_ctx)
 *
 * @retval MFD_SUCCESS : success
 * @retval MFD_ERROR   : error. set will fail.
 *
 * This function will be called after the table level undo setup function
 * ifXTable_undo_setup has been called.
 *
 *@note
 * this function will only be called if a new value is set for this column.
 *
 * If there is any setup specific to a particular column (e.g. allocating
 * memory for a string), you should do that setup in this function, so it
 * won't be done unless it is necessary.
 */
int
ifLinkUpDownTrapEnable_undo_setup(ifXTable_rowreq_ctx * rowreq_ctx)
{
    DEBUGMSGTL(("verbose:ifXTable:ifLinkUpDownTrapEnable_undo_setup",
                "called\n"));

    /** should never get a NULL pointer */
    netsnmp_assert(NULL != rowreq_ctx);

    /*
     * TODO:455:o: |-> Setup ifLinkUpDownTrapEnable undo.
     */
    /*
     * copy ifLinkUpDownTrapEnable data
     * set rowreq_ctx->undo->ifLinkUpDownTrapEnable from rowreq_ctx->data.ifLinkUpDownTrapEnable
     */
    rowreq_ctx->undo->ifLinkUpDownTrapEnable =
        rowreq_ctx->data.ifLinkUpDownTrapEnable;


    return MFD_SUCCESS;
}                               /* ifLinkUpDownTrapEnable_undo_setup */

/**
 * Set the new value.
 *
 * @param rowreq_ctx
 *        Pointer to the users context. You should know how to
 *        manipulate the value from this object.
 * @param ifLinkUpDownTrapEnable_val
 *        A long containing the new value.
 */
int
ifLinkUpDownTrapEnable_set(ifXTable_rowreq_ctx * rowreq_ctx,
                           u_long ifLinkUpDownTrapEnable_val)
{

    DEBUGMSGTL(("verbose:ifXTable:ifLinkUpDownTrapEnable_set",
                "called\n"));

    /** should never get a NULL pointer */
    netsnmp_assert(NULL != rowreq_ctx);

    /*
     * TODO:461:M: |-> Set ifLinkUpDownTrapEnable value.
     * set ifLinkUpDownTrapEnable value in rowreq_ctx->data
     */
    rowreq_ctx->data.ifLinkUpDownTrapEnable = ifLinkUpDownTrapEnable_val;

    return MFD_SUCCESS;
}                               /* ifLinkUpDownTrapEnable_set */

/**
 * undo the previous set.
 *
 * @param rowreq_ctx
 *        Pointer to the users context.
 */
int
ifLinkUpDownTrapEnable_undo(ifXTable_rowreq_ctx * rowreq_ctx)
{

    DEBUGMSGTL(("verbose:ifXTable:ifLinkUpDownTrapEnable_undo",
                "called\n"));

    netsnmp_assert(NULL != rowreq_ctx);

    /*
     * TODO:456:o: |-> Clean up ifLinkUpDownTrapEnable undo.
     */
    /*
     * copy ifLinkUpDownTrapEnable data
     * set rowreq_ctx->data.ifLinkUpDownTrapEnable from rowreq_ctx->undo->ifLinkUpDownTrapEnable
     */
    rowreq_ctx->data.ifLinkUpDownTrapEnable =
        rowreq_ctx->undo->ifLinkUpDownTrapEnable;


    return MFD_SUCCESS;
}                               /* ifLinkUpDownTrapEnable_undo */

/*---------------------------------------------------------------------
 * IF-MIB::ifXEntry.ifPromiscuousMode
 * ifPromiscuousMode is subid 16 of ifXEntry.
 * Its status is Current, and its access level is ReadWrite.
 * OID: .1.3.6.1.2.1.31.1.1.1.16
 * Description:
This object has a value of false(2) if this interface only
            accepts packets/frames that are addressed to this station.
            This object has a value of true(1) when the station accepts
            all packets/frames transmitted on the media.  The value
            true(1) is only legal on certain types of media.  If legal,
            setting this object to a value of true(1) may require the
            interface to be reset before becoming effective.

            The value of ifPromiscuousMode does not affect the reception
            of broadcast and multicast packets/frames by the interface.
 *
 * Attributes:
 *   accessible 1     isscalar 0     enums  1      hasdefval 0
 *   readable   1     iscolumn 1     ranges 0      hashint   0
 *   settable   1
 *
 * Enum range: 2/8. Values:  true(1), false(2)
 *
 * Its syntax is TruthValue (based on perltype INTEGER)
 * The net-snmp type is ASN_INTEGER. The C type decl is long (u_long)
 */
/**
 * Check that the proposed new value is potentially valid.
 *
 * @param rowreq_ctx
 *        Pointer to the row request context.
 * @param ifPromiscuousMode_val
 *        A long containing the new value.
 *
 * @retval MFD_SUCCESS        : incoming value is legal
 * @retval MFD_NOT_VALID_NOW  : incoming value is not valid now
 * @retval MFD_NOT_VALID_EVER : incoming value is never valid
 *
 * This is the place to check for requirements that are not
 * expressed in the mib syntax (for example, a requirement that
 * is detailed in the description for an object).
 *
 * You should check that the requested change between the undo value and the
 * new value is legal (ie, the transistion from one value to another
 * is legal).
 *      
 *@note
 * This check is only to determine if the new value
 * is \b potentially valid. This is the first check of many, and
 * is one of the simplest ones.
 * 
 *@note
 * this is not the place to do any checks for values
 * which depend on some other value in the mib. Those
 * types of checks should be done in the
 * ifXTable_check_dependencies() function.
 *
 * The following checks have already been done for you:
 *    The syntax is ASN_INTEGER
 *    The value is one of  true(1), false(2)
 *
 * If there a no other checks you need to do, simply return MFD_SUCCESS.
 *
 */
int
ifPromiscuousMode_check_value(ifXTable_rowreq_ctx * rowreq_ctx,
                              u_long ifPromiscuousMode_val)
{
    DEBUGMSGTL(("verbose:ifXTable:ifPromiscuousMode_check_value",
                "called\n"));

    /** should never get a NULL pointer */
    netsnmp_assert(NULL != rowreq_ctx);

    /*
     * TODO:441:o: |-> Check for valid ifPromiscuousMode value.
     */

    return MFD_SUCCESS;         /* ifPromiscuousMode value not illegal */
}                               /* ifPromiscuousMode_check_value */

/**
 * Save old value information
 *
 * @param rowreq_ctx
 *        Pointer to the table context (ifXTable_rowreq_ctx)
 *
 * @retval MFD_SUCCESS : success
 * @retval MFD_ERROR   : error. set will fail.
 *
 * This function will be called after the table level undo setup function
 * ifXTable_undo_setup has been called.
 *
 *@note
 * this function will only be called if a new value is set for this column.
 *
 * If there is any setup specific to a particular column (e.g. allocating
 * memory for a string), you should do that setup in this function, so it
 * won't be done unless it is necessary.
 */
int
ifPromiscuousMode_undo_setup(ifXTable_rowreq_ctx * rowreq_ctx)
{
    DEBUGMSGTL(("verbose:ifXTable:ifPromiscuousMode_undo_setup",
                "called\n"));

    /** should never get a NULL pointer */
    netsnmp_assert(NULL != rowreq_ctx);

    /*
     * TODO:455:o: |-> Setup ifPromiscuousMode undo.
     */
#ifdef NETSNMP_ENABLE_PROMISCUOUSMODE_SET
    /*
     * copy ifPromiscuousMode data
     * set rowreq_ctx->undo->ifPromiscuousMode from rowreq_ctx->data.ifPromiscuousMode
     */
    rowreq_ctx->undo->ifPromiscuousMode =
        rowreq_ctx->data.ifPromiscuousMode;


    return MFD_SUCCESS;
#else
    return MFD_NOT_VALID_EVER;
#endif
}                               /* ifPromiscuousMode_undo_setup */

/**
 * Set the new value.
 *
 * @param rowreq_ctx
 *        Pointer to the users context. You should know how to
 *        manipulate the value from this object.
 * @param ifPromiscuousMode_val
 *        A long containing the new value.
 */
int
ifPromiscuousMode_set(ifXTable_rowreq_ctx * rowreq_ctx,
                      u_long ifPromiscuousMode_val)
{

    DEBUGMSGTL(("verbose:ifXTable:ifPromiscuousMode_set", "called\n"));

    /** should never get a NULL pointer */
    netsnmp_assert(NULL != rowreq_ctx);

    /*
     * TODO:461:M: |-> Set ifPromiscuousMode value.
     * set ifPromiscuousMode value in rowreq_ctx->data
     */
    rowreq_ctx->data.ifPromiscuousMode = ifPromiscuousMode_val;

    return MFD_SUCCESS;
}                               /* ifPromiscuousMode_set */

/**
 * undo the previous set.
 *
 * @param rowreq_ctx
 *        Pointer to the users context.
 */
int
ifPromiscuousMode_undo(ifXTable_rowreq_ctx * rowreq_ctx)
{

    DEBUGMSGTL(("verbose:ifXTable:ifPromiscuousMode_undo", "called\n"));

    netsnmp_assert(NULL != rowreq_ctx);

    /*
     * TODO:456:o: |-> Clean up ifPromiscuousMode undo.
     */
#ifdef NETSNMP_ENABLE_PROMISCUOUSMODE_SET
    /*
     * copy ifPromiscuousMode data
     * set rowreq_ctx->data.ifPromiscuousMode from rowreq_ctx->undo->ifPromiscuousMode
     */
    rowreq_ctx->data.ifPromiscuousMode =
        rowreq_ctx->undo->ifPromiscuousMode;
#endif

    return MFD_SUCCESS;
}                               /* ifPromiscuousMode_undo */

/*---------------------------------------------------------------------
 * IF-MIB::ifXEntry.ifAlias
 * ifAlias is subid 18 of ifXEntry.
 * Its status is Current, and its access level is ReadWrite.
 * OID: .1.3.6.1.2.1.31.1.1.1.18
 * Description:
This object is an 'alias' name for the interface as
            specified by a network manager, and provides a non-volatile
            'handle' for the interface.

            On the first instantiation of an interface, the value of
            ifAlias associated with that interface is the zero-length
            string.  As and when a value is written into an instance of
            ifAlias through a network management set operation, then the
            agent must retain the supplied value in the ifAlias instance
            associated with the same interface for as long as that
            interface remains instantiated, including across all re-
            initializations/reboots of the network management system,
            including those which result in a change of the interface's
            ifIndex value.

            An example of the value which a network manager might store
            in this object for a WAN interface is the (Telco's) circuit
            number/identifier of the interface.

            Some agents may support write-access only for interfaces
            having particular values of ifType.  An agent which supports
            write access to this object is required to keep the value in
            non-volatile storage, but it may limit the length of new
            values depending on how much storage is already occupied by
            the current values for other interfaces.
 *
 * Attributes:
 *   accessible 1     isscalar 0     enums  0      hasdefval 0
 *   readable   1     iscolumn 1     ranges 1      hashint   1
 *   settable   1
 *   hint: 255a
 *
 * Ranges:  0 - 64;
 *
 * Its syntax is DisplayString (based on perltype OCTETSTR)
 * The net-snmp type is ASN_OCTET_STR. The C type decl is char (char)
 * This data type requires a length.  (Max 64)
 */
/**
 * Check that the proposed new value is potentially valid.
 *
 * @param rowreq_ctx
 *        Pointer to the row request context.
 * @param ifAlias_val_ptr
 *        A char containing the new value.
 * @param ifAlias_val_ptr_len
 *        The size (in bytes) of the data pointed to by ifAlias_val_ptr
 *
 * @retval MFD_SUCCESS        : incoming value is legal
 * @retval MFD_NOT_VALID_NOW  : incoming value is not valid now
 * @retval MFD_NOT_VALID_EVER : incoming value is never valid
 *
 * This is the place to check for requirements that are not
 * expressed in the mib syntax (for example, a requirement that
 * is detailed in the description for an object).
 *
 * You should check that the requested change between the undo value and the
 * new value is legal (ie, the transistion from one value to another
 * is legal).
 *      
 *@note
 * This check is only to determine if the new value
 * is \b potentially valid. This is the first check of many, and
 * is one of the simplest ones.
 * 
 *@note
 * this is not the place to do any checks for values
 * which depend on some other value in the mib. Those
 * types of checks should be done in the
 * ifXTable_check_dependencies() function.
 *
 * The following checks have already been done for you:
 *    The syntax is ASN_OCTET_STR
 *    The length is < sizeof(rowreq_ctx->data.ifAlias).
 *    The length is in (one of) the range set(s):  0 - 64
 *
 * If there a no other checks you need to do, simply return MFD_SUCCESS.
 *
 */
int
ifAlias_check_value(ifXTable_rowreq_ctx * rowreq_ctx,
                    char *ifAlias_val_ptr, size_t ifAlias_val_ptr_len)
{
    DEBUGMSGTL(("verbose:ifXTable:ifAlias_check_value", "called\n"));

    /** should never get a NULL pointer */
    netsnmp_assert(NULL != rowreq_ctx);
    netsnmp_assert(NULL != ifAlias_val_ptr);

    /*
     * TODO:441:o: |-> Check for valid ifAlias value.
     */

    return MFD_SUCCESS;         /* ifAlias value not illegal */
}                               /* ifAlias_check_value */

/**
 * Save old value information
 *
 * @param rowreq_ctx
 *        Pointer to the table context (ifXTable_rowreq_ctx)
 *
 * @retval MFD_SUCCESS : success
 * @retval MFD_ERROR   : error. set will fail.
 *
 * This function will be called after the table level undo setup function
 * ifXTable_undo_setup has been called.
 *
 *@note
 * this function will only be called if a new value is set for this column.
 *
 * If there is any setup specific to a particular column (e.g. allocating
 * memory for a string), you should do that setup in this function, so it
 * won't be done unless it is necessary.
 */
int
ifAlias_undo_setup(ifXTable_rowreq_ctx * rowreq_ctx)
{
    DEBUGMSGTL(("verbose:ifXTable:ifAlias_undo_setup", "called\n"));

    /** should never get a NULL pointer */
    netsnmp_assert(NULL != rowreq_ctx);

    /*
     * TODO:455:o: |-> Setup ifAlias undo.
     */
    /*
     * copy ifAlias and ifAlias_len data
     * set rowreq_ctx->undo->ifAlias from rowreq_ctx->data.ifAlias
     */
    memcpy(rowreq_ctx->undo->ifAlias, rowreq_ctx->data.ifAlias,
           (rowreq_ctx->data.ifAlias_len *
            sizeof(rowreq_ctx->undo->ifAlias[0])));
    rowreq_ctx->undo->ifAlias_len = rowreq_ctx->data.ifAlias_len;


    return MFD_SUCCESS;
}                               /* ifAlias_undo_setup */

/**
 * Set the new value.
 *
 * @param rowreq_ctx
 *        Pointer to the users context. You should know how to
 *        manipulate the value from this object.
 * @param ifAlias_val_ptr
 *        A char containing the new value.
 * @param ifAlias_val_ptr_len
 *        The size (in bytes) of the data pointed to by ifAlias_val_ptr
 */
int
ifAlias_set(ifXTable_rowreq_ctx * rowreq_ctx, char *ifAlias_val_ptr,
            size_t ifAlias_val_ptr_len)
{

    DEBUGMSGTL(("verbose:ifXTable:ifAlias_set", "called\n"));

    /** should never get a NULL pointer */
    netsnmp_assert(NULL != rowreq_ctx);
    netsnmp_assert(NULL != ifAlias_val_ptr);

    /*
     * TODO:461:M: |-> Set ifAlias value.
     * set ifAlias value in rowreq_ctx->data
     */
    memcpy(rowreq_ctx->data.ifAlias, ifAlias_val_ptr, ifAlias_val_ptr_len);
    /** convert bytes to number of char */
    rowreq_ctx->data.ifAlias_len =
        ifAlias_val_ptr_len / sizeof(ifAlias_val_ptr[0]);

    return MFD_SUCCESS;
}                               /* ifAlias_set */

/**
 * undo the previous set.
 *
 * @param rowreq_ctx
 *        Pointer to the users context.
 */
int
ifAlias_undo(ifXTable_rowreq_ctx * rowreq_ctx)
{

    DEBUGMSGTL(("verbose:ifXTable:ifAlias_undo", "called\n"));

    netsnmp_assert(NULL != rowreq_ctx);

    /*
     * TODO:456:o: |-> Clean up ifAlias undo.
     */
    /*
     * copy ifAlias and ifAlias_len data
     * set rowreq_ctx->data.ifAlias from rowreq_ctx->undo->ifAlias
     */
    memcpy(rowreq_ctx->data.ifAlias, rowreq_ctx->undo->ifAlias,
           (rowreq_ctx->undo->ifAlias_len *
            sizeof(rowreq_ctx->data.ifAlias[0])));
    rowreq_ctx->data.ifAlias_len = rowreq_ctx->undo->ifAlias_len;


    return MFD_SUCCESS;
}                               /* ifAlias_undo */

/**
 * check dependencies
 *
 * This is useful for for tables which have dependencies between columns
 * (or rows, or tables). For example, two columns allocating a percentage
 * of something add up 100%.
 *
 * Should you need different behavior depending on which columns were
 * set, rowreq_ctx->column_set_flags will indicate which writeable columns were
 * set. The definitions for the COLUMN_*_FLAG bits can be found in
 * ifXTable.h.
 * A new row will have the MFD_ROW_CREATED bit set in rowreq_flags.
 *
 * @retval MFD_SUCCESS all the changes to the row are legal
 * @retval MFD_ERROR   one or more changes are not legal
 *
 * (see README-table-ifXTable if you don't have dependencies)
 */
int
ifXTable_check_dependencies(ifXTable_rowreq_ctx * rowreq_ctx)
{
    int             rc = MFD_SUCCESS;

    DEBUGMSGTL(("internal:ifXTable:ifXTable_check_dependencies",
                "called\n"));

    netsnmp_assert(NULL != rowreq_ctx);

    /*
     * TODO:470:o: Check ifXTable row dependencies.
     * check that all new value are legal and consistent with each other
     */
    return rc;
}                               /* ifXTable_check_dependencies */

/** @} */
/** @{ */
