Exemple #1
0
int
handle_memsize(netsnmp_mib_handler *handler,
                netsnmp_handler_registration *reginfo,
                netsnmp_agent_request_info *reqinfo,
                netsnmp_request_info *requests)
{
    netsnmp_memory_info *mem_info;
    int val;

    /*
     * We just need to handle valid GET requests, as invalid instances
     *   are rejected automatically, and (valid) GETNEXT requests are
     *   converted into the appropriate GET request.
     *
     * We also only ever receive one request at a time.
     */
    switch (reqinfo->mode) {
    case MODE_GET:
        netsnmp_memory_load();
        mem_info = netsnmp_memory_get_byIdx( NETSNMP_MEM_TYPE_PHYSMEM, 0 );
        if ( !mem_info || mem_info->size == -1 || mem_info->units == -1 )
            netsnmp_set_request_error( reqinfo, requests, SNMP_NOSUCHOBJECT );
	else {
            val  =  mem_info->size;     /* memtotal */
            val *= (mem_info->units/1024);
            snmp_set_var_typed_value(requests->requestvb, ASN_INTEGER,
                                     (u_char *)&val, sizeof(val));
        }
        return SNMP_ERR_NOERROR;

    default:
        /*
         * we should never get here, so this is a really bad error 
         */
        snmp_log(LOG_ERR, "unknown mode (%d) in handle_memsize\n",
                 reqinfo->mode);
        return SNMP_ERR_GENERR;
    }

    return SNMP_ERR_NOERROR;
}
Exemple #2
0
static int
handle_snmp(netsnmp_mib_handler *handler,
	    netsnmp_handler_registration *reginfo,
	    netsnmp_agent_request_info *reqinfo,
	    netsnmp_request_info *requests)
{
    switch (reqinfo->mode) {
    case MODE_GET:
	{
	    oid idx = requests->requestvb->name[OID_LENGTH(snmp_oid)];
	    switch(idx) {
	    case 7:
	    case 23:
            case 30:
		netsnmp_set_request_error(reqinfo, requests,
					  SNMP_NOSUCHOBJECT);
		break;
	    default:
		{
		    u_int value =
			snmp_get_statistic(idx - 1 + STAT_SNMPINPKTS);
		    snmp_set_var_typed_value(requests->requestvb, ASN_COUNTER,
					     (u_char *)&value, sizeof(value));
		}
		break;
	    }
	}
	break;

    default:
        snmp_log(LOG_ERR,
                 "unknown mode (%d) in handle_snmp\n", reqinfo->mode);
        return SNMP_ERR_GENERR;
    }

    return SNMP_ERR_NOERROR;
}
int
_mfd_ipv4InterfaceTable_set_values(netsnmp_mib_handler *handler,
                                   netsnmp_handler_registration *reginfo,
                                   netsnmp_agent_request_info *agtreq_info,
                                   netsnmp_request_info *requests)
{
    ipv4InterfaceTable_rowreq_ctx *rowreq_ctx =
        netsnmp_container_table_row_extract(requests);
    netsnmp_table_request_info *tri;
    int             rc = SNMP_ERR_NOERROR;

    DEBUGMSGTL(("internal:ipv4InterfaceTable:_mfd_ipv4InterfaceTable_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 = _ipv4InterfaceTable_set_column(rowreq_ctx,
                                            requests->requestvb,
                                            tri->colnum);
        if (MFD_SUCCESS != rc) {
            DEBUGMSGTL(("ipv4InterfaceTable:mfd", "error %d from "
                        "ipv4InterfaceTable_set_column\n", rc));
            netsnmp_set_request_error(agtreq_info, requests,
                                      SNMP_VALIDATE_ERR(rc));
        }
    }                           /* for results */

    return SNMP_ERR_NOERROR;
}                               /* _mfd_ipv4InterfaceTable_set_values */
int
cpqNicIfLogMapOverallCondition_handler(netsnmp_mib_handler          *handler,
               netsnmp_handler_registration *reginfo,
               netsnmp_agent_request_info   *reqinfo,
               netsnmp_request_info         *requests)
{
    long val = 0;

    switch (reqinfo->mode) {
    case MODE_GET:
        switch (requests->requestvb->name[ reginfo->rootoid_len - 2 ]) {
            case CPQNICIFLOGMAPOVERALLCONDITION:
                val = get_cpqNicIfLogMapOverallCondition();
                break;
            default:
                /*
                 * An unsupported/unreadable column (if applicable)
                 */
                snmp_log(LOG_ERR, "unknown object (%lu) in cpqNicIfLogMapOverallCondition_handler\n",
                     requests->requestvb->name[ reginfo->rootoid_len - 2 ]);
                netsnmp_set_request_error( reqinfo, requests,
                                            SNMP_NOSUCHOBJECT );
                return SNMP_ERR_NOERROR;
        }
        snmp_set_var_typed_value(requests->requestvb, ASN_INTEGER,
                                 (u_char *)&val, sizeof(val));
        break;

    default:
        snmp_log(LOG_ERR, "unknown mode (%d) in cpqNicIfLogMapOverallCondition_handler\n",
                 reqinfo->mode);
        return SNMP_ERR_GENERR;
    }

    return SNMP_ERR_NOERROR;

}
int
get_timestamp(netsnmp_mib_handler * handler,
	netsnmp_handler_registration * reginfo,
	netsnmp_agent_request_info * reqinfo,
	netsnmp_request_info * requests)
{
	/*
	 * This handler returns the date and time of the current data
	 * collection. If the collection has not completed, it returns
	 * an SNMP_ERR_NOACCESS error.
	 *
	 * This handler is never called for a getnext if it is registered as
	 * an instance. An instance handler only delivers one request at a
	 * time, so we do not need to loop over a list of requests.
	 */
	DEBUGMSGTL(("demo_module_10", "get_timestamp CALLED\n"));

	switch (reqinfo->mode) {
	case MODE_GET:
		// A data collection is ready. Return its timestamp.
		if (status == 2)
			snmp_set_var_typed_value(requests->requestvb,
			    ASN_OCTET_STR, (u_char *)refreshTime,
			    sizeof (refreshTime));
		else
			// no data collection, so no timestamp available.
			netsnmp_set_request_error(reqinfo, requests,
                                      SNMP_ERR_NOACCESS);
		break;
	default:
		/*
		 * We should never get here, so this is a really bad error.
		 */
		return (SNMP_ERR_GENERR);
	}
	return (SNMP_ERR_NOERROR);
}
/** handles requests for the dot11WtpWirelessCapStatTable table */
int
dot11WtpWirelessCapStatTable_handler(
    netsnmp_mib_handler               *handler,
    netsnmp_handler_registration      *reginfo,
    netsnmp_agent_request_info        *reqinfo,
    netsnmp_request_info              *requests) {


    netsnmp_request_info       *request;
    netsnmp_table_request_info *table_info;
    struct dot11WtpWirelessCapStatTable_entry          *table_entry;

    switch (reqinfo->mode) {
        /*
         * Read-support (also covers GetNext requests)
         */
    case MODE_GET:
        for (request=requests; request; request=request->next) {
			
            table_entry = (struct dot11WtpWirelessCapStatTable_entry *)
                              netsnmp_extract_iterator_context(request);
            table_info  =     netsnmp_extract_table_info(      request);
           
			if( !table_entry )
			{
					netsnmp_set_request_error(reqinfo,request,SNMP_NOSUCHINSTANCE);
					continue;
				}	  
            switch (table_info->colnum) {
            case COLUMN_AVGRXSIGNALSTRENGTH:
			{   
                void *connection = NULL;
                if(SNMPD_DBUS_ERROR == get_instance_dbus_connection(table_entry->parameter, &connection, SNMPD_INSTANCE_MASTER_V3))
                    break;
                    
				int ret = 0;
				int AvgRxSignalStrength = 0;
				DCLI_WTP_API_GROUP_TWO *WTPINFO;
				char value[256] = { 0 };
				memset(value,0,256);
				char snr_avg[256] = { 0 };
				memset(snr_avg,0,256);
				strncpy(value,"-",sizeof(value)-1);	
				ret=show_wtp_wifi_snr_func(table_entry->parameter, connection,table_entry->wtpCurrID,&WTPINFO);
				if(ret==1)
				{
					if((WTPINFO)&&(WTPINFO->WTP[0]))
					{
						AvgRxSignalStrength = WTPINFO->WTP[0]->wtp_wifi_snr_stats.snr_average;
					}
					snprintf(snr_avg,sizeof(snr_avg)-1,"%d",AvgRxSignalStrength);
					strncat(value,snr_avg,sizeof(value)-strlen(value)-1);
					strncat(value,"dB",sizeof(value)-strlen(value)-1);
				}
				else if(SNMPD_CONNECTION_ERROR == ret) {
                    close_slot_dbus_connection(table_entry->parameter.slot_id);
    	        }
    	        
                snmp_set_var_typed_value( request->requestvb, ASN_OCTET_STR,
                                          (u_char*)value,
                                          strlen(value));
				if(ret==1)
				{
					free_show_wtp_wifi_snr(WTPINFO);
				}
            }
                break;
            case COLUMN_HIGHESTRXSIGNALSTRENGTH:
			{
                void *connection = NULL;
                if(SNMPD_DBUS_ERROR == get_instance_dbus_connection(table_entry->parameter, &connection, SNMPD_INSTANCE_MASTER_V3))
                    break;
                    
				int ret = 0;
				int HighestRxSignalStrength = 0;
				DCLI_WTP_API_GROUP_TWO *WTPINFO;
				char value[256] = { 0 };
				memset(value,0,256);
				char snr_max[256] = { 0 };
				memset(snr_max,0,256);
				strncpy(value,"-",sizeof(value)-1);				
				ret=show_wtp_wifi_snr_func(table_entry->parameter, connection,table_entry->wtpCurrID,&WTPINFO);
				if(ret==1)
				{
					if((WTPINFO)&&(WTPINFO->WTP[0]))
					{
						HighestRxSignalStrength = WTPINFO->WTP[0]->wtp_wifi_snr_stats.snr_max;
					}
					snprintf(snr_max,sizeof(snr_max)-1,"%d",HighestRxSignalStrength);
					strncat(value,snr_max,sizeof(value)-strlen(value)-1);
					strncat(value,"dB",sizeof(value)-strlen(value)-1);
				}
				else if(SNMPD_CONNECTION_ERROR == ret) {
                    close_slot_dbus_connection(table_entry->parameter.slot_id);
    	        }
    	        
                snmp_set_var_typed_value( request->requestvb, ASN_OCTET_STR,
                                          (u_char*)value,
                                          strlen(value));
				if(ret==1)
				{
					free_show_wtp_wifi_snr(WTPINFO);
				}
            }
                break;
            case COLUMN_LOWESTRXSIGNALSTRENGTH:
			{
                void *connection = NULL;
                if(SNMPD_DBUS_ERROR == get_instance_dbus_connection(table_entry->parameter, &connection, SNMPD_INSTANCE_MASTER_V3))
                    break;
                    
				int ret = 0;
				int LowestRxSignalStrength=0;
				DCLI_WTP_API_GROUP_TWO *WTPINFO;
                char value[256] = { 0 };
				memset(value,0,256);
				char snr_min[256] = { 0 };
				memset(snr_min,0,256);
				strncpy(value,"-",sizeof(value)-1);		
				ret=show_wtp_wifi_snr_func(table_entry->parameter, connection,table_entry->wtpCurrID,&WTPINFO);
				if(ret==1)
				{
					if((WTPINFO)&&(WTPINFO->WTP[0]))
					{
						if((WTPINFO->WTP[0]->wtp_wifi_snr_stats.snr_min) == 100)
						{
							LowestRxSignalStrength=0;
						}
						else
						{
							LowestRxSignalStrength	=WTPINFO->WTP[0]->wtp_wifi_snr_stats.snr_min;
						}					
					}
				
					snprintf(snr_min,sizeof(snr_min)-1,"%d",LowestRxSignalStrength);
					strncat(value,snr_min,sizeof(value)-strlen(value)-1);
					strncat(value,"dB",sizeof(value)-strlen(value)-1);
				}
				else if(SNMPD_CONNECTION_ERROR == ret) {
                    close_slot_dbus_connection(table_entry->parameter.slot_id);
    	        }
    	        
                snmp_set_var_typed_value( request->requestvb, ASN_OCTET_STR,
                                          (u_char*)value,
                                          strlen(value));
				if(ret==1)
				{
					free_show_wtp_wifi_snr(WTPINFO);
				}
            }
                break;
            case COLUMN_CHSTATSPHYERRPKTS:
			{
                void *connection = NULL;
                if(SNMPD_DBUS_ERROR == get_instance_dbus_connection(table_entry->parameter, &connection, SNMPD_INSTANCE_MASTER_V3))
                    break;
                    
			    int ret = 0;
				unsigned int PhyErrors = 0; 
				DCLI_AC_API_GROUP_THREE *statics = NULL;
				wlan_stats_info *head = NULL;

				ret=show_ap_statistics_list_bywtp(table_entry->parameter, connection,table_entry->wtpCurrID,&statics);
				if(ret==1)
				{
					if((statics)&&(statics->ap_statics_list)&&(statics->ap_statics_list->ap_statics_ele))
					{						
						head = statics->ap_statics_list->ap_statics_ele;
						while(head)
						{	
							if((head->type == 2)&&(head->wlanId == (table_entry->wtpWirelessIfIndex-1)))
							{
								PhyErrors = head->ast_rx_phyerr; 
								break;
							}
							head = head->next;
						}
					}
				}
				else if(SNMPD_CONNECTION_ERROR == ret) {
                    close_slot_dbus_connection(table_entry->parameter.slot_id);
    	        }
    	        
				table_entry->ChstatsPhyerrPkts = PhyErrors;
                snmp_set_var_typed_value( request->requestvb, ASN_COUNTER,
                                          (u_char*)&table_entry->ChstatsPhyerrPkts,
                                          sizeof(long));
				     if(ret==1)
					{
						Free_ap_statistics_head(statics);
					}
			}
                break;
            case COLUMN_CHSTATSFRAMERETRYCNT:
			{
                void *connection = NULL;
                if(SNMPD_DBUS_ERROR == get_instance_dbus_connection(table_entry->parameter, &connection, SNMPD_INSTANCE_MASTER_V3))
                    break;
                    
				int ret =  0;
				DCLI_WTP_API_GROUP_TWO *WTPINFO = NULL;
				ret  = show_wtp_extension_information_v4_func(table_entry->parameter, connection,table_entry->wtpCurrID,&WTPINFO);
				if((ret == 1)&&(WTPINFO)&&(WTPINFO->WTP[0]))
				{ 
				  table_entry->ChstatsFrameRetryCnt = WTPINFO->WTP[0]->wifi_extension_info.tx_retry;
				}
				else if(SNMPD_CONNECTION_ERROR == ret) {
                    close_slot_dbus_connection(table_entry->parameter.slot_id);
    	        }
    	        
                snmp_set_var_typed_value( request->requestvb, ASN_COUNTER,
                                      (u_char*)&table_entry->ChstatsFrameRetryCnt,
                                      sizeof(long));
				if(ret == 1)
				{ 
				  free_show_wtp_extension_information_v4(WTPINFO);
				}
            }
                break;
            case COLUMN_CHSTATSFRAMEERRORCNT:
			{
                void *connection = NULL;
                if(SNMPD_DBUS_ERROR == get_instance_dbus_connection(table_entry->parameter, &connection, SNMPD_INSTANCE_MASTER_V3))
                    break;
                    
			    int ret = 0;
				unsigned int RxErrors = 0; 
				DCLI_AC_API_GROUP_THREE *statics = NULL;
				wlan_stats_info *head = NULL;
				
				ret=show_ap_statistics_list_bywtp(table_entry->parameter, connection,table_entry->wtpCurrID,&statics);
				if(ret==1)
				{
					if((statics)&&(statics->ap_statics_list)&&(statics->ap_statics_list->ap_statics_ele))
					{						
						head = statics->ap_statics_list->ap_statics_ele;
						while(head)
						{	
							if((head->type == 2)&&(head->wlanId == (table_entry->wtpWirelessIfIndex-1)))
							{
								RxErrors = head->rx_errors; 
								break;
							}
							head = head->next;
						}
					}
				}
				else if(SNMPD_CONNECTION_ERROR == ret) {
                    close_slot_dbus_connection(table_entry->parameter.slot_id);
    	        }
    	        
					
                snmp_set_var_typed_value( request->requestvb, ASN_COUNTER,
                                          (u_char*)&table_entry->ChstatsFrameErrorCnt,
                                          sizeof(long));
			    if(ret==1)
				{
					Free_ap_statistics_head(statics);
				}
			}
                break;
            }
        }
        break;

    }
    return SNMP_ERR_NOERROR;
}
Exemple #7
0
/** handles requests for the nsModuleTable table, if anything else needs to be done */
int
nsModuleTable_handler(netsnmp_mib_handler *handler,
                      netsnmp_handler_registration *reginfo,
                      netsnmp_agent_request_info *reqinfo,
                      netsnmp_request_info *requests)
{

    netsnmp_table_request_info *table_info;
    netsnmp_request_info *request;
    netsnmp_variable_list *var;
    netsnmp_subtree *tree;
    u_long          ultmp;
    u_char          modes[1];

    for (request = requests; request; request = request->next) {
        var = request->requestvb;
        if (request->processed != 0)
            continue;

        /*
         * perform anything here that you need to do.  The request have
         * already been processed by the master table_dataset handler, but
         * this gives you chance to act on the request in some other way if
         * need be.
         */

        /*
         * the following extracts the my_data_context pointer set in the
         * loop functions above.  You can then use the results to help
         * return data for the columns of the nsModuleTable table in
         * question
         */
        tree = (netsnmp_subtree *)netsnmp_extract_iterator_context(request);
        if (tree == NULL) {
            if (reqinfo->mode == MODE_GET) {
                netsnmp_set_request_error(reqinfo, request,
                                          SNMP_NOSUCHINSTANCE);
                continue;
            }
            /*
             * XXX: no row existed, if you support creation and this is a
             * set, start dealing with it here, else continue
             */
        }

        /*
         * extracts the information about the table from the request
         */
        table_info = netsnmp_extract_table_info(request);

        /*
         * table_info->colnum contains the column number requested
         */
        /*
         * table_info->indexes contains a linked list of snmp variable
         * bindings for the indexes of the table.  Values in the list have
         * been set corresponding to the indexes of the request
         */
        if (table_info == NULL) {
            continue;
        }

        switch (reqinfo->mode) {
        /*
         * the table_iterator helper should change all GETNEXTs into
         * GETs for you automatically, so you don't have to worry
         * about the GETNEXT case.  Only GETs and SETs need to be
         * dealt with here
         */
        case MODE_GET:
            switch (table_info->colnum) {
            case COLUMN_NSMODULENAME:
                if (tree->reginfo->handlerName) {
                    snmp_set_var_typed_value(var, ASN_OCTET_STR,
                                             tree->reginfo->handlerName,
                                             strlen(tree->reginfo->handlerName));
                } else {
                    snmp_set_var_typed_value(var, ASN_OCTET_STR, "", 0);
                }
                break;

            case COLUMN_NSMODULEMODES:
                /*
                 * basically, these BITS needs to be inverted in order
                 */
                modes[0] =
                    ((HANDLER_CAN_GETANDGETNEXT & tree->reginfo->
                      modes) << 7) | ((HANDLER_CAN_SET & tree->reginfo->
                                       modes) << 5) | ((HANDLER_CAN_GETBULK
                                                        & tree->reginfo->
                                                        modes) << 3);
                /*  yuck  */
                snmp_set_var_typed_value(var, ASN_OCTET_STR, modes, 1);
                break;

            case COLUMN_NSMODULETIMEOUT:
                ultmp = tree->timeout;
                snmp_set_var_typed_value(var, ASN_INTEGER,
                                         (u_char *) & ultmp,
                                         sizeof(u_long));
                break;

            default:
                /*
                 * We shouldn't get here
                 */
                snmp_log(LOG_ERR,
                         "problem encountered in nsModuleTable_handler: unknown column\n");
            }
            break;

        default:
            snmp_log(LOG_ERR,
                     "problem encountered in nsModuleTable_handler: unsupported mode\n");
        }
    }
    return SNMP_ERR_NOERROR;
}
/** handles requests for the sipOtherStatsTable table.
 * For every request it checks the specified object to see if it has a
 * handler, and calls it */
static int sipOtherStatsTable_handler(
		netsnmp_mib_handler               *handler,
		netsnmp_handler_registration      *reginfo,
		netsnmp_agent_request_info        *reqinfo,
		netsnmp_request_info              *requests) 
{
	netsnmp_variable_list *var;
	netsnmp_table_request_info *table_info;
	struct sip_snmp_handler *h;
	struct sip_snmp_obj *o;
	const char *func = "snmp_mod";
	int res;
	void *tmp_val;
	size_t tmp_len;

	while(requests) {
		var = requests->requestvb;
		if(requests->processed != 0)
			goto next;
		table_info = netsnmp_extract_table_info(requests);
		if(!table_info)
			goto next;
		/* this is not an error, since table-walks work by trying to get
		 * things until we run off of it */
		if(table_info->colnum > SIPOTHERSTATSTABLE_COLUMNS)
			goto next;

		/* Get the handler and its object */
		if(sipOtherStatsTable_gh) {
			h = sipOtherStatsTable_gh;
			/* sip_obj is valid since we create upon registration */
			h->sip_obj->opaque = (void*)sipOtherStatsTable_replaceRow;
		} else {
			h = sipOtherStatsTable_h[table_info->colnum];
			if(!h) 
				goto next;
		}
		o = h->sip_obj;
		if(!o) {	/* bad bad boy... */
			LOG(L_ERR, "%s: Found handler without an object!!!\n", func);
			goto next;
		}
		o->col = table_info->colnum;
		o->row = var->name[var->name_length-1];
		switch(reqinfo->mode) {
			case MODE_GET:
			case MODE_GETNEXT:
				if(!h->on_get) break;
				res = h->on_get(o, SER_GET);
				if(res == -1) {
					/* since we don't have a way of knowing what went wrong,
					 * just use a generic error code */
					netsnmp_set_request_error(reqinfo, requests,
							SNMP_ERR_RESOURCEUNAVAILABLE);
					break;
				} else if(res == 0)
					/* the handler has new value to pass back up */
					snmp_set_var_typed_value(var, ser_types[o->type],
							(u_char*)o->value.voidp, o->val_len);
				break;
			case MODE_SET_RESERVE1:
				/* NOTE: We don't require the handler for a on_reserve
				 * function since for our cases it seems that just
				 * checking the type is enough */

				/* First make sure handler wants SETs */
				if(!h->on_set) break;
				/* Check the type */
				if(requests->requestvb->type != ser_types[o->type]) {
					LOG(L_ERR, "%s: Wrong type on SET processing\n", func);
					netsnmp_set_request_error(reqinfo, requests,
							SNMP_ERR_WRONGTYPE);
					break;
				}
				break;
			case MODE_SET_ACTION: /* the real deal */
				if(!h->on_set) break;
				/* copy in the new value for the handler */
				tmp_val = o->value.voidp;
				tmp_len = o->val_len;
				o->value.voidp = requests->requestvb->val.string;
				o->val_len = requests->requestvb->val_len;
				if(h->on_set(o, SER_SET) == -1) {
					LOG(L_ERR, "%s: SET Handler for object failed\n", func);
					netsnmp_set_request_error(reqinfo, requests,
						SNMP_ERR_RESOURCEUNAVAILABLE);
					o->value.voidp = tmp_val;
					o->val_len = tmp_len;
					break;
				}
				o->value.voidp = tmp_val;
				o->val_len = tmp_len;
				break;
			case MODE_SET_UNDO:
				if(!h->on_end) {
					if(h->on_set) /*tsk, tsk, bad boy, gonna tell your mamma..*/
						LOG(L_ERR, "%s: Found object without UNDO handler\n",
							func);
					break;
				}
				/* no point in checking for errors since we're already on
				 * an error branch */
				h->on_end(o, SER_UNDO);
				break;
			case MODE_SET_COMMIT:
				/* Tell the handler is all good and it can safely free up
				 * any memory it may have allocated for UNDO */
				if(!h->on_end) 
					break;
				h->on_end(o, SER_COMMIT);
				break;
			case MODE_SET_FREE:
				/* We get here on failure from RESERVE1. Since there we only 
				 * chk for type correctness, there's nothing to do here */
				break;
		}
next:
		requests = requests->next;
	}
	return SNMP_ERR_NOERROR;
}
Exemple #9
0
/** handles requests for the netSnmpHostsTable table, if anything else needs to be done */
int
netSnmpHostsTable_handler(netsnmp_mib_handler *handler,
                          netsnmp_handler_registration *reginfo,
                          netsnmp_agent_request_info *reqinfo,
                          netsnmp_request_info *requests)
{

    netsnmp_request_info *request;
    netsnmp_table_request_info *table_info;
    struct commitInfo *ci = NULL;

    void           *data_context = NULL;

    for (request = requests; request; request = request->next) {
        /* column and row index encoded portion */
        netsnmp_variable_list *var = request->requestvb;
        const oid * const suffix = var->name + reginfo->rootoid_len + 1;
        const size_t suffix_len = var->name_length - (reginfo->rootoid_len + 1);

        if (request->processed != 0)
            continue;

        switch (reqinfo->mode) {
        case MODE_GET:
        case MODE_SET_RESERVE1:
            data_context = netsnmp_extract_iterator_context(request);
            if (data_context == NULL) {
                if (reqinfo->mode == MODE_GET) {
                    netsnmp_set_request_error(reqinfo, request,
                                              SNMP_NOSUCHINSTANCE);
                    continue;
                }
            }
            break;

        default:               /* == the other SET modes */
            ci = netsnmp_oid_stash_get_data(commitStorage,
                                            suffix + 1, suffix_len - 1);
            break;

        }

        /** extracts the information about the table from the request */
        table_info = netsnmp_extract_table_info(request);
        /** table_info->colnum contains the column number requested */
        /** table_info->indexes contains a linked list of snmp variable
           bindings for the indexes of the table.  Values in the list
           have been set corresponding to the indexes of the
           request */
        if (table_info == NULL) {
            continue;
        }

        switch (reqinfo->mode) {
        case MODE_GET:
            switch (table_info->colnum) {
            case COLUMN_NETSNMPHOSTADDRESSTYPE:
                {
                    long           *retval;
                    size_t          retval_len = 0;
                    retval =
                        get_netSnmpHostAddressType(data_context,
                                                   &retval_len);
                    snmp_set_var_typed_value(var, ASN_INTEGER,
                                             (const u_char *) retval,
                                             retval_len);
                }
                break;

            case COLUMN_NETSNMPHOSTADDRESS:
                {
                    char           *retval;
                    size_t          retval_len = 0;
                    retval =
                        get_netSnmpHostAddress(data_context, &retval_len);
                    snmp_set_var_typed_value(var, ASN_OCTET_STR,
                                             (const u_char *) retval,
                                             retval_len);
                }
                break;

            case COLUMN_NETSNMPHOSTSTORAGE:
                {
                    long           *retval;
                    size_t          retval_len = 0;
                    retval =
                        get_netSnmpHostStorage(data_context, &retval_len);
                    snmp_set_var_typed_value(var, ASN_INTEGER,
                                             (const u_char *) retval,
                                             retval_len);
                }
                break;

            case COLUMN_NETSNMPHOSTROWSTATUS:
                {
                    long           *retval;
                    size_t          retval_len = 0;
                    retval =
                        get_netSnmpHostRowStatus(data_context,
                                                 &retval_len);
                    snmp_set_var_typed_value(var, ASN_INTEGER,
                                             (const u_char *) retval,
                                             retval_len);
                }
                break;

            default:
                /** We shouldn't get here */
                snmp_log(LOG_ERR,
                         "problem encountered in netSnmpHostsTable_handler: unknown column\n");
            }
            break;

        case MODE_SET_RESERVE1:
            ci = netsnmp_oid_stash_get_data(commitStorage,
                                            suffix + 1, suffix_len - 1);

            if (!ci) {
                    /** create the commit storage info */
                ci = SNMP_MALLOC_STRUCT(commitInfo);
                if (!data_context) {
                    ci->data_context =
                        netSnmpHostsTable_create_data_context(table_info->
                                                              indexes);
                    ci->new_row = 1;
                } else {
                    ci->data_context = data_context;
                }
                netsnmp_oid_stash_add_data(&commitStorage,
                                           suffix + 1, suffix_len - 1, ci);
            }
            break;

        case MODE_SET_RESERVE2:
            switch (table_info->colnum) {
            case COLUMN_NETSNMPHOSTADDRESSTYPE:
                {
                    long           *retval;
                    size_t          retval_len = 0;
                    struct undoInfo *ui = NULL;
                    int             ret;

                    /** first, get the old value */
                    retval =
                        get_netSnmpHostAddressType(ci->data_context,
                                                   &retval_len);
                    if (retval) {
                        ui = SNMP_MALLOC_STRUCT(undoInfo);
                        ui->len = retval_len;
                        memdup((u_char **) & ui->ptr,
                               (u_char *) retval, ui->len);
                    }

                    /** check the new value, possibly against the
                        older value for a valid state transition */
                    ret =
                        check_netSnmpHostAddressType(request->requestvb->
                                                     type,
                                                     (long *) request->
                                                     requestvb->val.string,
                                                     request->requestvb->
                                                     val_len, retval,
                                                     retval_len);
                    if (ret != 0) {
                        netsnmp_set_request_error(reqinfo, request, ret);
                        netSnmpHostsTable_free_undoInfo(ui);
                    } else if (ui) {
                        /** remember information for undo purposes later */
                        netsnmp_oid_stash_add_data(&undoStorage,
                                                   suffix, suffix_len, ui);
                    }

                }
                break;
            case COLUMN_NETSNMPHOSTADDRESS:
                {
                    char           *retval;
                    size_t          retval_len = 0;
                    struct undoInfo *ui = NULL;
                    int             ret;

                    /** first, get the old value */
                    retval =
                        get_netSnmpHostAddress(ci->data_context,
                                               &retval_len);
                    if (retval) {
                        ui = SNMP_MALLOC_STRUCT(undoInfo);
                        ui->len = retval_len;
                        memdup((u_char **) & ui->ptr,
                               (u_char *) retval, ui->len);
                    }

                    /** check the new value, possibly against the
                        older value for a valid state transition */
                    ret =
                        check_netSnmpHostAddress(request->requestvb->type,
                                                 (char *) request->
                                                 requestvb->val.string,
                                                 request->requestvb->
                                                 val_len, retval,
                                                 retval_len);
                    if (ret != 0) {
                        netsnmp_set_request_error(reqinfo, request, ret);
                        netSnmpHostsTable_free_undoInfo(ui);
                    } else if (ui) {
                        /** remember information for undo purposes later */
                        netsnmp_oid_stash_add_data(&undoStorage,
                                                   suffix, suffix_len, ui);
                    }

                }
                break;
            case COLUMN_NETSNMPHOSTSTORAGE:
                {
                    long           *retval;
                    size_t          retval_len = 0;
                    struct undoInfo *ui = NULL;
                    int             ret;

                    /** first, get the old value */
                    retval =
                        get_netSnmpHostStorage(ci->data_context,
                                               &retval_len);
                    if (retval) {
                        ui = SNMP_MALLOC_STRUCT(undoInfo);
                        ui->len = retval_len;
                        memdup((u_char **) & ui->ptr,
                               (u_char *) retval, ui->len);
                    }

                    /** check the new value, possibly against the
                        older value for a valid state transition */
                    ret =
                        check_netSnmpHostStorage(request->requestvb->type,
                                                 (long *) request->
                                                 requestvb->val.string,
                                                 request->requestvb->
                                                 val_len, retval,
                                                 retval_len);
                    if (ret != 0) {
                        netsnmp_set_request_error(reqinfo, request, ret);
                        netSnmpHostsTable_free_undoInfo(ui);
                    } else if (ui) {
                        /** remember information for undo purposes later */
                        netsnmp_oid_stash_add_data(&undoStorage,
                                                   suffix, suffix_len, ui);
                    }

                }
                break;
            case COLUMN_NETSNMPHOSTROWSTATUS:
                {
                    long           *retval;
                    size_t          retval_len = 0;
                    struct undoInfo *ui = NULL;
                    int             ret;

                    /** first, get the old value */
                    retval =
                        get_netSnmpHostRowStatus(ci->data_context,
                                                 &retval_len);
                    if (retval) {
                        ui = SNMP_MALLOC_STRUCT(undoInfo);
                        ui->len = retval_len;
                        memdup((u_char **) & ui->ptr,
                               (u_char *) retval, ui->len);
                    }

                    /** check the new value, possibly against the
                        older value for a valid state transition */
                    ret =
                        check_netSnmpHostRowStatus(request->requestvb->
                                                   type,
                                                   (long *) request->
                                                   requestvb->val.string,
                                                   request->requestvb->
                                                   val_len, retval,
                                                   retval_len);
                    if (ret != 0) {
                        netsnmp_set_request_error(reqinfo, request, ret);
                        netSnmpHostsTable_free_undoInfo(ui);
                    } else if (ui) {
                        /** remember information for undo purposes later */
                        netsnmp_oid_stash_add_data(&undoStorage,
                                                   suffix, suffix_len, ui);
                    }

                }
                break;
            default:
                netsnmp_set_request_error(reqinfo, request,
                                          SNMP_ERR_NOTWRITABLE);
                break;
            }
            break;

        case MODE_SET_ACTION:
            /** save a variable copy */
            switch (table_info->colnum) {
            case COLUMN_NETSNMPHOSTADDRESSTYPE:
                {
                    int             ret;
                    ret = set_netSnmpHostAddressType(ci->data_context,
                                                     (long *) request->
                                                     requestvb->val.string,
                                                     request->requestvb->
                                                     val_len);
                    if (ret) {
                        netsnmp_set_request_error(reqinfo, request, ret);
                    }
                }
                break;
            case COLUMN_NETSNMPHOSTADDRESS:
                {
                    int             ret;
                    ret = set_netSnmpHostAddress(ci->data_context,
                                                 (char *) request->
                                                 requestvb->val.string,
                                                 request->requestvb->
                                                 val_len);
                    if (ret) {
                        netsnmp_set_request_error(reqinfo, request, ret);
                    }
                }
                break;
            case COLUMN_NETSNMPHOSTSTORAGE:
                {
                    int             ret;
                    ret = set_netSnmpHostStorage(ci->data_context,
                                                 (long *) request->
                                                 requestvb->val.string,
                                                 request->requestvb->
                                                 val_len);
                    if (ret) {
                        netsnmp_set_request_error(reqinfo, request, ret);
                    }
                }
                break;
            case COLUMN_NETSNMPHOSTROWSTATUS:
                {
                    int             ret;
                    ret = set_netSnmpHostRowStatus(ci->data_context,
                                                   (long *) request->
                                                   requestvb->val.string,
                                                   request->requestvb->
                                                   val_len);
                    if (ret) {
                        netsnmp_set_request_error(reqinfo, request, ret);
                    }
                    if (*request->requestvb->val.integer == RS_DESTROY) {
                        ci->new_row = -1;
                    }
                }
                break;
            }
            break;

        case MODE_SET_COMMIT:
            if (!ci->have_committed) {
                    /** do this once per row only */
                netSnmpHostsTable_commit_row(&ci->data_context,
                                             ci->new_row);
                ci->have_committed = 1;
            }
            break;

        case MODE_SET_UNDO:
             /** save a variable copy */
            switch (table_info->colnum) {
            case COLUMN_NETSNMPHOSTADDRESSTYPE:
                {
                    int             retval;
                    struct undoInfo *ui;
                    ui = netsnmp_oid_stash_get_data(undoStorage,
                                                    suffix, suffix_len);
                    retval =
                        set_netSnmpHostAddressType(ci->data_context,
                                                   ui->ptr, ui->len);
                    if (retval) {
                        netsnmp_set_request_error(reqinfo, request,
                                                  SNMP_ERR_UNDOFAILED);
                    }
                }
                break;
            case COLUMN_NETSNMPHOSTADDRESS:
                {
                    int             retval;
                    struct undoInfo *ui;
                    ui = netsnmp_oid_stash_get_data(undoStorage,
                                                    suffix, suffix_len);
                    retval =
                        set_netSnmpHostAddress(ci->data_context, ui->ptr,
                                               ui->len);
                    if (retval) {
                        netsnmp_set_request_error(reqinfo, request,
                                                  SNMP_ERR_UNDOFAILED);
                    }
                }
                break;
            case COLUMN_NETSNMPHOSTSTORAGE:
                {
                    int             retval;
                    struct undoInfo *ui;
                    ui = netsnmp_oid_stash_get_data(undoStorage,
                                                    suffix, suffix_len);
                    retval =
                        set_netSnmpHostStorage(ci->data_context, ui->ptr,
                                               ui->len);
                    if (retval) {
                        netsnmp_set_request_error(reqinfo, request,
                                                  SNMP_ERR_UNDOFAILED);
                    }
                }
                break;
            case COLUMN_NETSNMPHOSTROWSTATUS:
                {
                    int             retval;
                    struct undoInfo *ui;
                    ui = netsnmp_oid_stash_get_data(undoStorage,
                                                    suffix, suffix_len);
                    retval =
                        set_netSnmpHostRowStatus(ci->data_context, ui->ptr,
                                                 ui->len);
                    if (retval) {
                        netsnmp_set_request_error(reqinfo, request,
                                                  SNMP_ERR_UNDOFAILED);
                    }
                }
                break;
            }
            break;

        case MODE_SET_FREE:
            break;

        default:
            snmp_log(LOG_ERR,
                     "problem encountered in netSnmpHostsTable_handler: unsupported mode\n");
        }
    }

    /** clean up after all requset processing has ended */
    switch (reqinfo->mode) {
    case MODE_SET_UNDO:
    case MODE_SET_FREE:
    case MODE_SET_COMMIT:
        /** clear out the undo cache */
        netsnmp_oid_stash_free(&undoStorage,
                               netSnmpHostsTable_free_undoInfo);
        netsnmp_oid_stash_free(&commitStorage, netsnmp_oid_stash_no_free);
    }


    return SNMP_ERR_NOERROR;
}
Exemple #10
0
static void process_set_group (netsnmp_index * o, void *c)
{
    /* xxx-rks: should we continue processing after an error?? */
    set_context *context = (set_context *) c;

    netsnmp_request_group *ag = (netsnmp_request_group *) o;

    int rc = SNMP_ERR_NOERROR;

    switch (context->agtreq_info->mode)
    {

    case MODE_SET_RESERVE1:
        /** -> SET_RESERVE2 || SET_FREE */

        /*
         * if not a new row, save undo info
         */
        if (ag->row_created == 0)
        {
            if (context->tad->cb->duplicate_row)
                ag->undo_info = context->tad->cb->duplicate_row (ag->existing_row);
            else
                ag->undo_info = NULL;
            if (NULL == ag->undo_info)
            {
                rc = SNMP_ERR_RESOURCEUNAVAILABLE;
                break;
            }
        }

        if (context->tad->cb->set_reserve1)
            context->tad->cb->set_reserve1 (ag);
        break;

    case MODE_SET_RESERVE2:
        /** -> SET_ACTION || SET_FREE */
        if (context->tad->cb->set_reserve2)
            context->tad->cb->set_reserve2 (ag);
        break;

    case MODE_SET_ACTION:
        /** -> SET_COMMIT || SET_UNDO */
        if (context->tad->cb->set_action)
            context->tad->cb->set_action (ag);
        break;

    case MODE_SET_COMMIT:
        /** FINAL CHANCE ON SUCCESS */
        if (ag->row_created == 0)
        {
            /*
             * this is an existing row, has it been deleted?
             */
            if (ag->row_deleted == 1)
            {
                DEBUGMSGT ((TABLE_ARRAY_NAME, "action: deleting row\n"));
                if (CONTAINER_REMOVE (ag->table, ag->existing_row) != 0)
                {
                    rc = SNMP_ERR_COMMITFAILED;
                    break;
                }
            }
        }
        else if (ag->row_deleted == 0)
        {
            /*
             * new row (that hasn't been deleted) should be inserted
             */
            DEBUGMSGT ((TABLE_ARRAY_NAME, "action: inserting row\n"));
            if (CONTAINER_INSERT (ag->table, ag->existing_row) != 0)
            {
                rc = SNMP_ERR_COMMITFAILED;
                break;
            }
        }

        if (context->tad->cb->set_commit)
            context->tad->cb->set_commit (ag);

        /** no more use for undo_info, so free it */
        if (ag->undo_info)
        {
            context->tad->cb->delete_row (ag->undo_info);
            ag->undo_info = NULL;
        }

#if 0
        /* XXX-rks: finish row cooperative notifications
         * if the table has requested it, send cooperative notifications
         * for row operations.
         */
        if (context->tad->notifications)
        {
            if (ag->undo_info)
            {
                if (!ag->existing_row)
                    netsnmp_monitor_notify (EVENT_ROW_DEL);
                else
                    netsnmp_monitor_notify (EVENT_ROW_MOD);
            }
            else
                netsnmp_monitor_notify (EVENT_ROW_ADD);
        }
#endif

        if ((ag->row_created == 0) && (ag->row_deleted == 1))
        {
            context->tad->cb->delete_row (ag->existing_row);
            ag->existing_row = NULL;
        }
        break;

    case MODE_SET_FREE:
        /** FINAL CHANCE ON FAILURE */
        if (context->tad->cb->set_free)
            context->tad->cb->set_free (ag);

        /** no more use for undo_info, so free it */
        if (ag->row_created == 1)
        {
            if (context->tad->cb->delete_row)
                context->tad->cb->delete_row (ag->existing_row);
            ag->existing_row = NULL;
        }
        else
        {
            if (context->tad->cb->delete_row)
                context->tad->cb->delete_row (ag->undo_info);
            ag->undo_info = NULL;
        }
        break;

    case MODE_SET_UNDO:
        /** FINAL CHANCE ON FAILURE */
        /*
         * status already set - don't change it now
         */
        if (context->tad->cb->set_undo)
            context->tad->cb->set_undo (ag);

        /*
         * no more use for undo_info, so free it
         */
        if (ag->row_created == 0)
        {
            /*
             * restore old values
             */
            context->tad->cb->row_copy (ag->existing_row, ag->undo_info);
            context->tad->cb->delete_row (ag->undo_info);
            ag->undo_info = NULL;
        }
        else
        {
            context->tad->cb->delete_row (ag->existing_row);
            ag->existing_row = NULL;
        }
        break;

    default:
        snmp_log (LOG_ERR, "unknown mode processing SET for " "netsnmp_table_array_helper_handler\n");
        rc = SNMP_ERR_GENERR;
        break;
    }

    if (rc)
        netsnmp_set_request_error (context->agtreq_info, ag->list->ri, rc);

}
Exemple #11
0
/**********************************************************************
 **********************************************************************
 *                                                                    *
 *                                                                    *
 * GET procession functions                                           *
 *                                                                    *
 *                                                                    *
 **********************************************************************
 **********************************************************************/
int
process_get_requests (netsnmp_handler_registration * reginfo,
                      netsnmp_agent_request_info * agtreq_info,
                      netsnmp_request_info * requests, table_container_data * tad)
{
    int rc = SNMP_ERR_NOERROR;

    netsnmp_request_info *current;

    netsnmp_index *row = NULL;

    netsnmp_table_request_info *tblreq_info;

    netsnmp_variable_list *var;

    /*
     * Loop through each of the requests, and
     * try to find the appropriate row from the container.
     */
    for (current = requests; current; current = current->next)
    {

        var = current->requestvb;
        DEBUGMSGTL (("table_array:get", "  process_get_request oid:"));
        DEBUGMSGOID (("table_array:get", var->name, var->name_length));
        DEBUGMSG (("table_array:get", "\n"));

        /*
         * skip anything that doesn't need processing.
         */
        if (current->processed != 0)
        {
            DEBUGMSGTL (("table_array:get", "already processed\n"));
            continue;
        }

        /*
         * Get pointer to the table information for this request. This
         * information was saved by table_helper_handler. When
         * debugging, we double check a few assumptions. For example,
         * the table_helper_handler should enforce column boundaries.
         */
        tblreq_info = netsnmp_extract_table_info (current);
        netsnmp_assert (tblreq_info->colnum <= tad->tblreg_info->max_column);

        if ((agtreq_info->mode == MODE_GETNEXT) || (agtreq_info->mode == MODE_GETBULK))
        {
            /*
             * find the row
             */
            row = netsnmp_table_index_find_next_row (tad->table, tblreq_info);
            if (!row)
            {
                /*
                 * no results found.
                 *
                 * xxx-rks: how do we skip this entry for the next handler,
                 * but still allow it a chance to hit another handler?
                 */
                DEBUGMSGTL (("table_array:get", "no row found\n"));
                netsnmp_set_request_error (agtreq_info, current, SNMP_ENDOFMIBVIEW);
                continue;
            }

            /*
             * * if data was found, make sure it has the column we want
             */

            /* xxx-rks: add suport for sparse tables */

            /*
             * build new oid
             */
            build_new_oid (reginfo, tblreq_info, row, current);

        } /** GETNEXT/GETBULK */
        else
        {
            netsnmp_index index;

            index.oids = tblreq_info->index_oid;
            index.len = tblreq_info->index_oid_len;

            row = (netsnmp_index *) CONTAINER_FIND (tad->table, &index);
            if (!row)
            {
                DEBUGMSGTL (("table_array:get", "no row found\n"));
                netsnmp_set_request_error (agtreq_info, current, SNMP_NOSUCHINSTANCE);
                continue;
            }

        } /** GET */

        /*
         * get the data
         */
        rc = tad->cb->get_value (current, row, tblreq_info);

    } /** for ( ... requests ... ) */

    return rc;
}
/** handles requests for the mteTriggerThresholdTable table */
int
mteTriggerThresholdTable_handler(netsnmp_mib_handler *handler,
                                 netsnmp_handler_registration *reginfo,
                                 netsnmp_agent_request_info *reqinfo,
                                 netsnmp_request_info *requests)
{

    netsnmp_request_info       *request;
    netsnmp_table_request_info *tinfo;
    struct mteTrigger          *entry;
    int ret;

    DEBUGMSGTL(("disman:event:mib", "Threshold Table handler (%d)\n",
                                     reqinfo->mode));

    switch (reqinfo->mode) {
        /*
         * Read-support (also covers GetNext requests)
         */
    case MODE_GET:
        for (request = requests; request; request = request->next) {
            entry = (struct mteTrigger *) netsnmp_tdata_extract_entry(request);
            tinfo = netsnmp_extract_table_info(request);

            /*
             * The mteTriggerThresholdTable should only contains entries for
             *   rows where the mteTriggerTest 'threshold(2)' bit is set.
             * So skip entries where this isn't the case.
             */
            if (!entry || !(entry->mteTriggerTest & MTE_TRIGGER_THRESHOLD ))
                continue;

            switch (tinfo->colnum) {
            case COLUMN_MTETRIGGERTHRESHOLDSTARTUP:
                snmp_set_var_typed_integer(request->requestvb, ASN_INTEGER,
                                           entry->mteTThStartup);
                break;
            case COLUMN_MTETRIGGERTHRESHOLDRISING:
                snmp_set_var_typed_integer(request->requestvb, ASN_INTEGER,
                                           entry->mteTThRiseValue);
                break;
            case COLUMN_MTETRIGGERTHRESHOLDFALLING:
                snmp_set_var_typed_integer(request->requestvb, ASN_INTEGER,
                                           entry->mteTThFallValue);
                break;
            case COLUMN_MTETRIGGERTHRESHOLDDELTARISING:
                snmp_set_var_typed_integer(request->requestvb, ASN_INTEGER,
                                           entry->mteTThDRiseValue);
                break;
            case COLUMN_MTETRIGGERTHRESHOLDDELTAFALLING:
                snmp_set_var_typed_integer(request->requestvb, ASN_INTEGER,
                                           entry->mteTThDFallValue);
                break;
            case COLUMN_MTETRIGGERTHRESHOLDOBJECTSOWNER:
                snmp_set_var_typed_value(request->requestvb, ASN_OCTET_STR,
                              (u_char *) entry->mteTThObjOwner,
                                  strlen(entry->mteTThObjOwner));
                break;
            case COLUMN_MTETRIGGERTHRESHOLDOBJECTS:
                snmp_set_var_typed_value(request->requestvb, ASN_OCTET_STR,
                              (u_char *) entry->mteTThObjects,
                                  strlen(entry->mteTThObjects));
                break;
            case COLUMN_MTETRIGGERTHRESHOLDRISINGEVENTOWNER:
                snmp_set_var_typed_value(request->requestvb, ASN_OCTET_STR,
                              (u_char *) entry->mteTThRiseOwner,
                                  strlen(entry->mteTThRiseOwner));
                break;
            case COLUMN_MTETRIGGERTHRESHOLDRISINGEVENT:
                snmp_set_var_typed_value(request->requestvb, ASN_OCTET_STR,
                              (u_char *) entry->mteTThRiseEvent,
                                  strlen(entry->mteTThRiseEvent));
                break;
            case COLUMN_MTETRIGGERTHRESHOLDFALLINGEVENTOWNER:
                snmp_set_var_typed_value(request->requestvb, ASN_OCTET_STR,
                              (u_char *) entry->mteTThFallOwner,
                                  strlen(entry->mteTThFallOwner));
                break;
            case COLUMN_MTETRIGGERTHRESHOLDFALLINGEVENT:
                snmp_set_var_typed_value(request->requestvb, ASN_OCTET_STR,
                              (u_char *) entry->mteTThFallEvent,
                                  strlen(entry->mteTThFallEvent));
                break;
            case COLUMN_MTETRIGGERTHRESHOLDDELTARISINGEVENTOWNER:
                snmp_set_var_typed_value(request->requestvb, ASN_OCTET_STR,
                              (u_char *) entry->mteTThDRiseOwner,
                                  strlen(entry->mteTThDRiseOwner));
                break;
            case COLUMN_MTETRIGGERTHRESHOLDDELTARISINGEVENT:
                snmp_set_var_typed_value(request->requestvb, ASN_OCTET_STR,
                              (u_char *) entry->mteTThDRiseEvent,
                                  strlen(entry->mteTThDRiseEvent));
                break;
            case COLUMN_MTETRIGGERTHRESHOLDDELTAFALLINGEVENTOWNER:
                snmp_set_var_typed_value(request->requestvb, ASN_OCTET_STR,
                              (u_char *) entry->mteTThDFallOwner,
                                  strlen(entry->mteTThDFallOwner));
                break;
            case COLUMN_MTETRIGGERTHRESHOLDDELTAFALLINGEVENT:
                snmp_set_var_typed_value(request->requestvb, ASN_OCTET_STR,
                              (u_char *) entry->mteTThDFallEvent,
                                  strlen(entry->mteTThDFallEvent));
                break;
            }
        }
        break;

#ifndef NETSNMP_NO_WRITE_SUPPORT
        /*
         * Write-support
         */
    case MODE_SET_RESERVE1:
        for (request = requests; request; request = request->next) {
            entry = (struct mteTrigger *) netsnmp_tdata_extract_entry(request);
            tinfo = netsnmp_extract_table_info(request);

            /*
             * Since the mteTriggerThresholdTable only contains entries for
             *   rows where the mteTriggerTest 'threshold(2)' bit is set,
             *   strictly speaking we should reject assignments where
             *   this isn't the case.
             * But SET requests that include an assignment of the
             *   'threshold(2)' bit at the same time are valid, so would
             *    need to be accepted. Unfortunately, this assignment
             *   is only applied in the COMMIT pass, so it's difficult
             *   to detect whether this holds or not.
             *
             * Let's fudge things for now, by processing assignments
             *   even if the 'threshold(2)' bit isn't set.
             */
            switch (tinfo->colnum) {
            case COLUMN_MTETRIGGERTHRESHOLDSTARTUP:
                ret = netsnmp_check_vb_int_range(request->requestvb,
                                                 MTE_THRESH_START_RISE,
                                                 MTE_THRESH_START_RISEFALL );
                if (ret != SNMP_ERR_NOERROR) {
                    netsnmp_set_request_error(reqinfo, request, ret);
                    return SNMP_ERR_NOERROR;
                }
                break;
            case COLUMN_MTETRIGGERTHRESHOLDRISING:
            case COLUMN_MTETRIGGERTHRESHOLDFALLING:
            case COLUMN_MTETRIGGERTHRESHOLDDELTARISING:
            case COLUMN_MTETRIGGERTHRESHOLDDELTAFALLING:
                ret = netsnmp_check_vb_int(request->requestvb);
                if (ret != SNMP_ERR_NOERROR) {
                    netsnmp_set_request_error(reqinfo, request, ret);
                    return SNMP_ERR_NOERROR;
                }
                break;
            case COLUMN_MTETRIGGERTHRESHOLDOBJECTSOWNER:
            case COLUMN_MTETRIGGERTHRESHOLDOBJECTS:
            case COLUMN_MTETRIGGERTHRESHOLDRISINGEVENTOWNER:
            case COLUMN_MTETRIGGERTHRESHOLDRISINGEVENT:
            case COLUMN_MTETRIGGERTHRESHOLDFALLINGEVENTOWNER:
            case COLUMN_MTETRIGGERTHRESHOLDFALLINGEVENT:
            case COLUMN_MTETRIGGERTHRESHOLDDELTARISINGEVENTOWNER:
            case COLUMN_MTETRIGGERTHRESHOLDDELTARISINGEVENT:
            case COLUMN_MTETRIGGERTHRESHOLDDELTAFALLINGEVENTOWNER:
            case COLUMN_MTETRIGGERTHRESHOLDDELTAFALLINGEVENT:
                ret = netsnmp_check_vb_type_and_max_size(
                          request->requestvb, ASN_OCTET_STR, MTE_STR1_LEN);
                if (ret != SNMP_ERR_NOERROR) {
                    netsnmp_set_request_error(reqinfo, request, ret);
                    return SNMP_ERR_NOERROR;
                }
                break;
            default:
                netsnmp_set_request_error(reqinfo, request,
                                          SNMP_ERR_NOTWRITABLE);
                return SNMP_ERR_NOERROR;
            }

            /*
             * The Event MIB is somewhat ambiguous as to whether the
             *  various trigger table entries can be modified once the
             *  main mteTriggerTable entry has been marked 'active'. 
             * But it's clear from discussion on the DisMan mailing
             *  list is that the intention is not.
             *
             * So check for whether this row is already active,
             *  and reject *all* SET requests if it is.
             */
            entry = (struct mteTrigger *) netsnmp_tdata_extract_entry(request);
            if (entry &&
                entry->flags & MTE_TRIGGER_FLAG_ACTIVE ) {
                netsnmp_set_request_error(reqinfo, request,
                                          SNMP_ERR_INCONSISTENTVALUE);
                return SNMP_ERR_NOERROR;
            }
        }
        break;

    case MODE_SET_RESERVE2:
    case MODE_SET_FREE:
    case MODE_SET_UNDO:
        break;

    case MODE_SET_ACTION:
        for (request = requests; request; request = request->next) {
            entry = (struct mteTrigger *) netsnmp_tdata_extract_entry(request);
            if (!entry) {
                /*
                 * New rows must be created via the RowStatus column
                 *   (in the main mteTriggerTable)
                 */
                netsnmp_set_request_error(reqinfo, request,
                                          SNMP_ERR_NOCREATION);
                                      /* or inconsistentName? */
                return SNMP_ERR_NOERROR;
            }
        }
        break;

    case MODE_SET_COMMIT:
        /*
         * All these assignments are "unfailable", so it's
         *  (reasonably) safe to apply them in the Commit phase
         */
        for (request = requests; request; request = request->next) {
            entry = (struct mteTrigger *) netsnmp_tdata_extract_entry(request);
            tinfo = netsnmp_extract_table_info(request);

            switch (tinfo->colnum) {
            case COLUMN_MTETRIGGERTHRESHOLDSTARTUP:
                entry->mteTThStartup    = *request->requestvb->val.integer;
                break;
            case COLUMN_MTETRIGGERTHRESHOLDRISING:
                entry->mteTThRiseValue  = *request->requestvb->val.integer;
                break;
            case COLUMN_MTETRIGGERTHRESHOLDFALLING:
                entry->mteTThFallValue  = *request->requestvb->val.integer;
                break;
            case COLUMN_MTETRIGGERTHRESHOLDDELTARISING:
                entry->mteTThDRiseValue = *request->requestvb->val.integer;
                break;
            case COLUMN_MTETRIGGERTHRESHOLDDELTAFALLING:
                entry->mteTThDFallValue = *request->requestvb->val.integer;
                break;
            case COLUMN_MTETRIGGERTHRESHOLDOBJECTSOWNER:
                memset(entry->mteTThObjOwner, 0, sizeof(entry->mteTThObjOwner));
                memcpy(entry->mteTThObjOwner, request->requestvb->val.string,
                                              request->requestvb->val_len);
                break;
            case COLUMN_MTETRIGGERTHRESHOLDOBJECTS:
                memset(entry->mteTThObjects,  0, sizeof(entry->mteTThObjects));
                memcpy(entry->mteTThObjects,  request->requestvb->val.string,
                                              request->requestvb->val_len);
                break;
            case COLUMN_MTETRIGGERTHRESHOLDRISINGEVENTOWNER:
                memset(entry->mteTThRiseOwner, 0, sizeof(entry->mteTThRiseOwner));
                memcpy(entry->mteTThRiseOwner, request->requestvb->val.string,
                                               request->requestvb->val_len);
                break;
            case COLUMN_MTETRIGGERTHRESHOLDRISINGEVENT:
                memset(entry->mteTThRiseEvent, 0, sizeof(entry->mteTThRiseEvent));
                memcpy(entry->mteTThRiseEvent, request->requestvb->val.string,
                                               request->requestvb->val_len);
                break;
            case COLUMN_MTETRIGGERTHRESHOLDFALLINGEVENTOWNER:
                memset(entry->mteTThFallOwner, 0, sizeof(entry->mteTThFallOwner));
                memcpy(entry->mteTThFallOwner, request->requestvb->val.string,
                                               request->requestvb->val_len);
                break;
            case COLUMN_MTETRIGGERTHRESHOLDFALLINGEVENT:
                memset(entry->mteTThFallEvent, 0, sizeof(entry->mteTThFallEvent));
                memcpy(entry->mteTThFallEvent, request->requestvb->val.string,
                                               request->requestvb->val_len);
                break;
            case COLUMN_MTETRIGGERTHRESHOLDDELTARISINGEVENTOWNER:
                memset(entry->mteTThDRiseOwner, 0, sizeof(entry->mteTThDRiseOwner));
                memcpy(entry->mteTThDRiseOwner, request->requestvb->val.string,
                                                request->requestvb->val_len);
                break;
            case COLUMN_MTETRIGGERTHRESHOLDDELTARISINGEVENT:
                memset(entry->mteTThDRiseEvent, 0, sizeof(entry->mteTThDRiseEvent));
                memcpy(entry->mteTThDRiseEvent, request->requestvb->val.string,
                                                request->requestvb->val_len);
                break;
            case COLUMN_MTETRIGGERTHRESHOLDDELTAFALLINGEVENTOWNER:
                memset(entry->mteTThDFallOwner, 0, sizeof(entry->mteTThDFallOwner));
                memcpy(entry->mteTThDFallOwner, request->requestvb->val.string,
                                                request->requestvb->val_len);
                break;
            case COLUMN_MTETRIGGERTHRESHOLDDELTAFALLINGEVENT:
                memset(entry->mteTThDFallEvent, 0, sizeof(entry->mteTThDFallEvent));
                memcpy(entry->mteTThDFallEvent, request->requestvb->val.string,
                                                request->requestvb->val_len);
                break;
            }
        }
        break;
#endif /* !NETSNMP_NO_WRITE_SUPPORT */

    }
    return SNMP_ERR_NOERROR;
}
Exemple #13
0
int
handle_ipForwarding(netsnmp_mib_handler *handler,
                          netsnmp_handler_registration *reginfo,
                          netsnmp_agent_request_info   *reqinfo,
                          netsnmp_request_info         *requests)
{
    int      rc;
    u_long   value;

    /* We are never called for a GETNEXT if it's registered as a
       "instance", as it's "magically" handled for us.  */

    /* a instance handler also only hands us one request at a time, so
       we don't need to loop over a list of requests; we'll only get one. */

    switch(reqinfo->mode) {

        case MODE_GET:
            rc = netsnmp_arch_ip_scalars_ipForwarding_get(&value);
            if (rc != 0) {
                netsnmp_set_request_error(reqinfo, requests,
                                      SNMP_NOSUCHINSTANCE);
            }
            else {
                value = value ? 1 : 2;
                snmp_set_var_typed_value(requests->requestvb, ASN_INTEGER,
                                     (u_char *)&value, sizeof(value));
            }
            break;

        /*
         * SET REQUEST
         *
         * multiple states in the transaction.  See:
         * http://www.net-snmp.org/tutorial-5/toolkit/mib_module/set-actions.jpg
         */
        case MODE_SET_RESERVE1:
            break;

        case MODE_SET_RESERVE2:
            /*
             * store old info for undo later
             */
            rc = netsnmp_arch_ip_scalars_ipForwarding_get(&value);
            if (rc < 0) {
                netsnmp_set_request_error(reqinfo, requests,
                                          SNMP_ERR_NOCREATION);
            } else {
                u_long *value_save = NULL;
				u_char * _value_save = (u_char *)value_save;
                memdup(& _value_save, (u_char *) &value,
                       sizeof(value));
                if ( NULL == value_save )
                    netsnmp_set_request_error(reqinfo, requests, SNMP_ERR_RESOURCEUNAVAILABLE);
                else
                    netsnmp_request_add_list_data(requests,
                                                  netsnmp_create_data_list
                                                  ("ipfw", value_save,
                                                  free));
	    }
            break;

        case MODE_SET_FREE:
            /* XXX: free resources allocated in RESERVE1 and/or
               RESERVE2.  Something failed somewhere, and the states
               below won't be called. */
            break;

        case MODE_SET_ACTION:
            /* XXX: perform the value change here */
            value =  *(requests->requestvb->val.integer);
            rc = netsnmp_arch_ip_scalars_ipForwarding_set(value);
            if ( 0 != rc ) {
                netsnmp_set_request_error(reqinfo, requests, rc);
            }
            break;

        case MODE_SET_COMMIT:
            break;

        case MODE_SET_UNDO:
             value =
                 *((u_long *) netsnmp_request_get_list_data(requests,
                                                            "ipfw"));
             rc = netsnmp_arch_ip_scalars_ipForwarding_set(value);
             if ( 0 != rc ) {
                 netsnmp_set_request_error(reqinfo, requests, SNMP_ERR_UNDOFAILED);
             }
             break;

        default:
            /* we should never get here, so this is a really bad error */
            snmp_log(LOG_ERR, "unknown mode (%d) in handle_ipForwarding\n", reqinfo->mode );
            return SNMP_ERR_GENERR;
    }

    return SNMP_ERR_NOERROR;
}
Exemple #14
0
int
handle_ipAddressSpinLock(netsnmp_mib_handler *handler,
                          netsnmp_handler_registration *reginfo,
                          netsnmp_agent_request_info   *reqinfo,
                          netsnmp_request_info         *requests)
{
    u_long   value;

    /* We are never called for a GETNEXT if it's registered as a
       "instance", as it's "magically" handled for us.  */

    /* a instance handler also only hands us one request at a time, so
       we don't need to loop over a list of requests; we'll only get one. */

    switch(reqinfo->mode) {

        case MODE_GET:
            snmp_set_var_typed_value(requests->requestvb, ASN_INTEGER,
                                     (u_char *)&ipAddressSpinLockValue, 
                                     sizeof(ipAddressSpinLockValue));
            break;

        /*
         * SET REQUEST
         *
         * multiple states in the transaction.  See:
         * http://www.net-snmp.org/tutorial-5/toolkit/mib_module/set-actions.jpg
         */
        case MODE_SET_RESERVE1:
        case MODE_SET_RESERVE2:
            /* just check the value */
            value =  *(requests->requestvb->val.integer);
            if (value != ipAddressSpinLockValue)
                netsnmp_set_request_error(reqinfo, requests, SNMP_ERR_INCONSISTENTVALUE);
            break;

        case MODE_SET_FREE:
            break;

        case MODE_SET_ACTION:
            /* perform the final spinlock check and increase its value */
            value =  *(requests->requestvb->val.integer);
            if (value != ipAddressSpinLockValue) {
                netsnmp_set_request_error(reqinfo, requests, SNMP_ERR_INCONSISTENTVALUE);
            } else {
                ipAddressSpinLockValue++;
                /* and check it for overflow */
                if (ipAddressSpinLockValue > 2147483647 || ipAddressSpinLockValue < 0)
                    ipAddressSpinLockValue = 0;
            }
            break;

        case MODE_SET_COMMIT:
            break;

        case MODE_SET_UNDO:
             break;

        default:
            /* we should never get here, so this is a really bad error */
            snmp_log(LOG_ERR, "unknown mode (%d) in handle_ipAddressSpinLock\n", reqinfo->mode );
            return SNMP_ERR_GENERR;
    }

    return SNMP_ERR_NOERROR;
}
Exemple #15
0
/** handles requests for the mteEventTable table */
int
mteEventTable_handler(netsnmp_mib_handler *handler,
                      netsnmp_handler_registration *reginfo,
                      netsnmp_agent_request_info *reqinfo,
                      netsnmp_request_info *requests)
{

    netsnmp_request_info       *request;
    netsnmp_table_request_info *tinfo;
    netsnmp_tdata_row          *row;
    struct mteEvent            *entry;
    char mteOwner[MTE_STR1_LEN+1];
    char mteEName[MTE_STR1_LEN+1];
    long ret;

    DEBUGMSGTL(("disman:event:mib", "Event Table handler (%d)\n",
                                     reqinfo->mode));

    switch (reqinfo->mode) {
        /*
         * Read-support (also covers GetNext requests)
         */
    case MODE_GET:
        for (request = requests; request; request = request->next) {
            if (request->processed)
                continue;

            entry = (struct mteEvent *) netsnmp_tdata_extract_entry(request);
            tinfo = netsnmp_extract_table_info(request);
            if (!entry || !(entry->flags & MTE_EVENT_FLAG_VALID))
                continue;

            switch (tinfo->colnum) {
            case COLUMN_MTEEVENTCOMMENT:
                snmp_set_var_typed_value(request->requestvb, ASN_OCTET_STR,
                                         entry->mteEventComment,
                                  strlen(entry->mteEventComment));
                break;
            case COLUMN_MTEEVENTACTIONS:
                snmp_set_var_typed_value(request->requestvb, ASN_OCTET_STR,
                                        &entry->mteEventActions, 1);
                break;
            case COLUMN_MTEEVENTENABLED:
                ret = (entry->flags & MTE_EVENT_FLAG_ENABLED ) ?
                           TV_TRUE : TV_FALSE;
                snmp_set_var_typed_integer(request->requestvb, ASN_INTEGER, ret);
                break;
            case COLUMN_MTEEVENTENTRYSTATUS:
                ret = (entry->flags & MTE_EVENT_FLAG_ACTIVE ) ?
                           RS_ACTIVE : RS_NOTINSERVICE;
                snmp_set_var_typed_integer(request->requestvb, ASN_INTEGER, ret);
                break;
            }
        }
        break;


#ifndef NETSNMP_NO_WRITE_SUPPORT
        /*
         * Write-support
         */
    case MODE_SET_RESERVE1:
        for (request = requests; request; request = request->next) {
            if (request->processed)
                continue;

            entry = (struct mteEvent *) netsnmp_tdata_extract_entry(request);
            tinfo = netsnmp_extract_table_info(request);

            switch (tinfo->colnum) {
            case COLUMN_MTEEVENTCOMMENT:
                ret = netsnmp_check_vb_type_and_max_size(
                          request->requestvb, ASN_OCTET_STR, MTE_STR1_LEN);
                if (ret != SNMP_ERR_NOERROR) {
                    netsnmp_set_request_error(reqinfo, request, ret);
                    return SNMP_ERR_NOERROR;
                }
                /*
                 * Can't modify the comment of an active row
                 *   (No good reason for this, but that's what the MIB says!)
                 */
                if (entry &&
                    entry->flags & MTE_EVENT_FLAG_ACTIVE ) {
                    netsnmp_set_request_error(reqinfo, request,
                                              SNMP_ERR_INCONSISTENTVALUE);
                    return SNMP_ERR_NOERROR;
                }
                break;
            case COLUMN_MTEEVENTACTIONS:
                ret = netsnmp_check_vb_type_and_size(
                          request->requestvb, ASN_OCTET_STR, 1);
                if (ret != SNMP_ERR_NOERROR) {
                    netsnmp_set_request_error(reqinfo, request, ret);
                    return SNMP_ERR_NOERROR;
                }
                /*
                 * Can't modify the event types of an active row
                 *   (A little more understandable perhaps,
                 *    but still an unnecessary restriction IMO)
                 */
                if (entry &&
                    entry->flags & MTE_EVENT_FLAG_ACTIVE ) {
                    netsnmp_set_request_error(reqinfo, request,
                                              SNMP_ERR_INCONSISTENTVALUE);
                    return SNMP_ERR_NOERROR;
                }
                break;
            case COLUMN_MTEEVENTENABLED:
                ret = netsnmp_check_vb_truthvalue(request->requestvb);
                if (ret != SNMP_ERR_NOERROR) {
                    netsnmp_set_request_error(reqinfo, request, ret);
                    return SNMP_ERR_NOERROR;
                }
                /*
                 * The published version of the Event MIB forbids
                 *   enabling (or disabling) an active row, which
                 *   would make this object completely pointless!
                 * Fortunately this ludicrous decision has since been corrected.
                 */
                break;

            case COLUMN_MTEEVENTENTRYSTATUS:
                ret = netsnmp_check_vb_rowstatus(request->requestvb,
                          (entry ? RS_ACTIVE : RS_NONEXISTENT));
                if (ret != SNMP_ERR_NOERROR) {
                    netsnmp_set_request_error(reqinfo, request, ret);
                    return SNMP_ERR_NOERROR;
                }
                /* An active row can only be deleted */
                if (entry &&
                    entry->flags & MTE_EVENT_FLAG_ACTIVE &&
                    *request->requestvb->val.integer == RS_NOTINSERVICE ) {
                    netsnmp_set_request_error(reqinfo, request,
                                              SNMP_ERR_INCONSISTENTVALUE);
                    return SNMP_ERR_NOERROR;
                }
                break;
            default:
                netsnmp_set_request_error(reqinfo, request,
                                          SNMP_ERR_NOTWRITABLE);
                return SNMP_ERR_NOERROR;
            }
        }
        break;

    case MODE_SET_RESERVE2:
        for (request = requests; request; request = request->next) {
            if (request->processed)
                continue;

            tinfo = netsnmp_extract_table_info(request);

            switch (tinfo->colnum) {
            case COLUMN_MTEEVENTENTRYSTATUS:
                switch (*request->requestvb->val.integer) {
                case RS_CREATEANDGO:
                case RS_CREATEANDWAIT:
                    /*
                     * Create an (empty) new row structure
                     */
                    memset(mteOwner, 0, sizeof(mteOwner));
                    memcpy(mteOwner, tinfo->indexes->val.string,
                                     tinfo->indexes->val_len);
                    memset(mteEName, 0, sizeof(mteEName));
                    memcpy(mteEName,
                           tinfo->indexes->next_variable->val.string,
                           tinfo->indexes->next_variable->val_len);

                    row = mteEvent_createEntry(mteOwner, mteEName, 0);
                    if (!row) {
                        netsnmp_set_request_error(reqinfo, request,
                                                  SNMP_ERR_RESOURCEUNAVAILABLE);
                        return SNMP_ERR_NOERROR;
                    }
                    netsnmp_insert_tdata_row( request, row );
                }
            }
        }
        break;

    case MODE_SET_FREE:
        for (request = requests; request; request = request->next) {
            if (request->processed)
                continue;

            tinfo = netsnmp_extract_table_info(request);

            switch (tinfo->colnum) {
            case COLUMN_MTEEVENTENTRYSTATUS:
                switch (*request->requestvb->val.integer) {
                case RS_CREATEANDGO:
                case RS_CREATEANDWAIT:
                    /*
                     * Tidy up after a failed row creation request
                     */ 
                    entry = (struct mteEvent *)
                                netsnmp_tdata_extract_entry(request);
                    if (entry &&
                      !(entry->flags & MTE_EVENT_FLAG_VALID)) {
                        row = (netsnmp_tdata_row *)
                                netsnmp_tdata_extract_row(request);
                        mteEvent_removeEntry( row );
                    }
                }
            }
        }
        break;

    case MODE_SET_ACTION:
        for (request = requests; request; request = request->next) {
            if (request->processed)
                continue;

            tinfo = netsnmp_extract_table_info(request);
            entry = (struct mteEvent *) netsnmp_tdata_extract_entry(request);
            if (!entry) {
                /*
                 * New rows must be created via the RowStatus column
                 */
                netsnmp_set_request_error(reqinfo, request,
                                          SNMP_ERR_NOCREATION);
                                      /* or inconsistentName? */
                return SNMP_ERR_NOERROR;

            }
        }
        break;

    case MODE_SET_UNDO:
        break;

    case MODE_SET_COMMIT:
        /*
         * All these assignments are "unfailable", so it's
         *  (reasonably) safe to apply them in the Commit phase
         */
        for (request = requests; request; request = request->next) {
            if (request->processed)
                continue;

            entry = (struct mteEvent *) netsnmp_tdata_extract_entry(request);
            tinfo = netsnmp_extract_table_info(request);

            switch (tinfo->colnum) {
            case COLUMN_MTEEVENTCOMMENT:
                memset(entry->mteEventComment, 0,
                       sizeof(entry->mteEventComment));
                memcpy(entry->mteEventComment,
                       request->requestvb->val.string,
                       request->requestvb->val_len);
                break;

            case COLUMN_MTEEVENTACTIONS:
                entry->mteEventActions = request->requestvb->val.string[0];
                break;

            case COLUMN_MTEEVENTENABLED:
                if (*request->requestvb->val.integer == TV_TRUE)
                    entry->flags |=  MTE_EVENT_FLAG_ENABLED;
                else
                    entry->flags &= ~MTE_EVENT_FLAG_ENABLED;
                break;

            case COLUMN_MTEEVENTENTRYSTATUS:
                switch (*request->requestvb->val.integer) {
                case RS_ACTIVE:
                    entry->flags |= MTE_EVENT_FLAG_ACTIVE;
                    break;
                case RS_CREATEANDGO:
                    entry->flags |= MTE_EVENT_FLAG_ACTIVE;
                    /* fall-through */
                case RS_CREATEANDWAIT:
                    entry->flags |= MTE_EVENT_FLAG_VALID;
                    entry->session =
                        netsnmp_iquery_pdu_session(reqinfo->asp->pdu);
                    break;

                case RS_DESTROY:
                    row = (netsnmp_tdata_row *)
                               netsnmp_tdata_extract_row(request);
                    mteEvent_removeEntry(row);
                }
            }
        }
        break;
#endif /* !NETSNMP_NO_WRITE_SUPPORT */

    }
    DEBUGMSGTL(("disman:event:mib", "Table handler, done\n"));
    return SNMP_ERR_NOERROR;
}
/** handles requests for the dot11QosWirelessTable table */
int
dot11QosWirelessTable_handler(
    netsnmp_mib_handler               *handler,
    netsnmp_handler_registration      *reginfo,
    netsnmp_agent_request_info        *reqinfo,
    netsnmp_request_info              *requests) {

    netsnmp_request_info       *request;
    netsnmp_table_request_info *table_info;
    struct dot11QosWirelessTable_entry          *table_entry;

    switch (reqinfo->mode) {
        /*
         * Read-support (also covers GetNext requests)
         */
    case MODE_GET:
        for (request=requests; request; request=request->next) {
            table_entry = (struct dot11QosWirelessTable_entry *)
                              netsnmp_extract_iterator_context(request);
            table_info  =     netsnmp_extract_table_info(      request);			
			if( !table_entry )
			{
					netsnmp_set_request_error(reqinfo,request,SNMP_NOSUCHINSTANCE);
					continue;
				}	
				
            void *connection = NULL;
            if(SNMPD_DBUS_ERROR == get_slot_dbus_connection(table_entry->parameter.slot_id, &connection, SNMPD_INSTANCE_MASTER_V3))
                break;
    
            switch (table_info->colnum) {
            case COLUMN_WTPID:
                snmp_set_var_typed_value( request->requestvb, ASN_INTEGER,
                                          (u_char*)&table_entry->globalWtpID,
                                          sizeof(long));
                break;
            case COLUMN_RADIOLOCALID:
                snmp_set_var_typed_value( request->requestvb, ASN_INTEGER,
                                          (u_char*)&table_entry->RadioLocalID,
                                          sizeof(long));
                break;
            case COLUMN_QOSTYPE:
                snmp_set_var_typed_value( request->requestvb, ASN_INTEGER,
                                          (u_char*)&table_entry->QosType,
                                          sizeof(long));
                break;
            case COLUMN_QOSWIRELESSAIFS:
            {   
			    char wtpID[10] = { 0 };
				memset(wtpID,0,10);
				char type[20] = { 0 };
				memset(type,0,20);
				char radioID[10] = { 0 };
                memset(radioID,0,10);
				int ret = 0;
				DCLI_WQOS *WQOS = NULL;
				snprintf(wtpID,sizeof(wtpID)-1,"%d",table_entry->WtpID);
                snprintf(radioID,sizeof(radioID)-1,"%d",table_entry->RadioLocalID);

				if(table_entry->QosType == 1)
				{
					memset(type,0,20);
					strncpy(type,"BESTEFFORT",sizeof(type)-1);
				}
				else if(table_entry->QosType == 2)
				{
					memset(type,0,20);
	                strncpy(type,"BACKGROUND",sizeof(type)-1);
				}
				else if(table_entry->QosType == 3)
				{
					memset(type,0,20);
	                strncpy(type,"VIDEO",sizeof(type)-1);
				}
				else if(table_entry->QosType == 4)
				{
					memset(type,0,20);
	                strncpy(type,"VOICE",sizeof(type)-1);
				}				

				ret = wid_show_qos_radio_cmd(table_entry->parameter, connection,wtpID,radioID,type,&WQOS);
				if((ret == 1)&&(WQOS->qos[0])&&(WQOS->qos[0]->radio_qos[table_entry->QosType-1]))
				{
					table_entry->QosWirelessAIFS = WQOS->qos[0]->radio_qos[table_entry->QosType-1]->AIFS;
				}
				
                snmp_set_var_typed_value( request->requestvb, ASN_INTEGER,
                                          (u_char*)&table_entry->QosWirelessAIFS,
                                          sizeof(long));

				if(ret == 1)
				{
					Free_qos_one(WQOS);
				}
            }
                break;
            case COLUMN_QOSWIRELESSCWMIN:
			 {   
			    char wtpID[10] = { 0 };
				memset(wtpID,0,10);
				char type[20] = { 0 };
				memset(type,0,20);
				char radioID[10] = { 0 };
                memset(radioID,0,10);
				int ret = 0;
				DCLI_WQOS *WQOS = NULL;
				snprintf(wtpID,sizeof(wtpID)-1,"%d",table_entry->WtpID);
                snprintf(radioID,sizeof(radioID)-1,"%d",table_entry->RadioLocalID);

				if(table_entry->QosType == 1)
				{
					memset(type,0,20);
					strncpy(type,"BESTEFFORT",sizeof(type)-1);
				}
				else if(table_entry->QosType == 2)
				{
					memset(type,0,20);
	                strncpy(type,"BACKGROUND",sizeof(type)-1);
				}
				else if(table_entry->QosType == 3)
				{
					memset(type,0,20);
	                strncpy(type,"VIDEO",sizeof(type)-1);
				}
				else if(table_entry->QosType == 4)
				{
					memset(type,0,20);
	                strncpy(type,"VOICE",sizeof(type)-1);
				}
				
				ret = wid_show_qos_radio_cmd(table_entry->parameter, connection,wtpID,radioID,type,&WQOS);
				if((ret == 1)&&(WQOS->qos[0])&&(WQOS->qos[0]->radio_qos[table_entry->QosType-1]))
				{
					table_entry->QosWirelessCWmin = WQOS->qos[0]->radio_qos[table_entry->QosType-1]->CWMin;
				}
				
                snmp_set_var_typed_value( request->requestvb, ASN_INTEGER,
                                          (u_char*)&table_entry->QosWirelessCWmin,
                                          sizeof(long));

				if(ret == 1)
				{
					Free_qos_one(WQOS);
				}
            }
                break;
            case COLUMN_QOSWIRELESSCWMAX:
			{   
			    char wtpID[10] = { 0 };
				memset(wtpID,0,10);
				char type[20] = { 0 };
				memset(type,0,20);
				char radioID[10] = { 0 };
                memset(radioID,0,10);
				int ret = 0;
				DCLI_WQOS *WQOS = NULL;
				snprintf(wtpID,sizeof(wtpID)-1,"%d",table_entry->WtpID);
                snprintf(radioID,sizeof(radioID)-1,"%d",table_entry->RadioLocalID);

				if(table_entry->QosType == 1)
				{
					memset(type,0,20);
					strncpy(type,"BESTEFFORT",sizeof(type)-1);
				}
				else if(table_entry->QosType == 2)
				{
					memset(type,0,20);
	                strncpy(type,"BACKGROUND",sizeof(type)-1);
				}
				else if(table_entry->QosType == 3)
				{
					memset(type,0,20);
	                strncpy(type,"VIDEO",sizeof(type)-1);
				}
				else if(table_entry->QosType == 4)
				{
					memset(type,0,20);
	                strncpy(type,"VOICE",sizeof(type)-1);
				}
				
				ret = wid_show_qos_radio_cmd(table_entry->parameter, connection,wtpID,radioID,type,&WQOS);
				if((ret == 1)&&(WQOS->qos[0])&&(WQOS->qos[0]->radio_qos[table_entry->QosType-1]))
				{
					table_entry->QoSWirelessCWmax = WQOS->qos[0]->radio_qos[table_entry->QosType-1]->CWMax;
				}
				
                snmp_set_var_typed_value( request->requestvb, ASN_INTEGER,
                                          (u_char*)&table_entry->QoSWirelessCWmax,
                                          sizeof(long));

				if(ret == 1)
				{
					Free_qos_one(WQOS);
				}
            }
                break;
            case COLUMN_QOSWIRELESSTXOPLIM:
			{   
			    char wtpID[10] = { 0 };
				memset(wtpID,0,10);
				char type[20] = { 0 };
				memset(type,0,20);
				char radioID[10] = { 0 };
                memset(radioID,0,10);
				int ret = 0;
				DCLI_WQOS *WQOS = NULL;
				snprintf(wtpID,sizeof(wtpID)-1,"%d",table_entry->WtpID);
                snprintf(radioID,sizeof(radioID)-1,"%d",table_entry->RadioLocalID);

				if(table_entry->QosType == 1)
				{
					memset(type,0,20);
					strncpy(type,"BESTEFFORT",sizeof(type)-1);
				}
				else if(table_entry->QosType == 2)
				{
					memset(type,0,20);
	                strncpy(type,"BACKGROUND",sizeof(type)-1);
				}
				else if(table_entry->QosType == 3)
				{
					memset(type,0,20);
	                strncpy(type,"VIDEO",sizeof(type)-1);
				}
				else if(table_entry->QosType == 4)
				{
					memset(type,0,20);
	                strncpy(type,"VOICE",sizeof(type)-1);
				}
				
				ret = wid_show_qos_radio_cmd(table_entry->parameter, connection,wtpID,radioID,type,&WQOS);
				if((ret == 1)&&(WQOS->qos[0])&&(WQOS->qos[0]->radio_qos[table_entry->QosType-1]))
				{
					table_entry->QoSWirelessTXOPLim = WQOS->qos[0]->radio_qos[table_entry->QosType-1]->TXOPlimit;
				}
				
                snmp_set_var_typed_value( request->requestvb, ASN_INTEGER,
                                          (u_char*)&table_entry->QoSWirelessTXOPLim,                                          
                                          sizeof(long));

				if(ret == 1)
				{
					Free_qos_one(WQOS);
				}
            }
                break;
            }
        }
        break;

        /*
         * Write-support
         */
    case MODE_SET_RESERVE1:
        for (request=requests; request; request=request->next) {
            table_entry = (struct dot11QosWirelessTable_entry *)
                              netsnmp_extract_iterator_context(request);
            table_info  =     netsnmp_extract_table_info(      request);
    
            switch (table_info->colnum) {
            case COLUMN_QOSWIRELESSAIFS:
                if ( request->requestvb->type != ASN_INTEGER ) {
                    netsnmp_set_request_error( reqinfo, request,
                                               SNMP_ERR_WRONGTYPE );
                    return SNMP_ERR_NOERROR;
                }
                /* Also may need to check size/value */
                break;
            case COLUMN_QOSWIRELESSCWMIN:
                if ( request->requestvb->type != ASN_INTEGER ) {
                    netsnmp_set_request_error( reqinfo, request,
                                               SNMP_ERR_WRONGTYPE );
                    return SNMP_ERR_NOERROR;
                }
                /* Also may need to check size/value */
                break;
            case COLUMN_QOSWIRELESSCWMAX:
                if ( request->requestvb->type != ASN_INTEGER ) {
                    netsnmp_set_request_error( reqinfo, request,
                                               SNMP_ERR_WRONGTYPE );
                    return SNMP_ERR_NOERROR;
                }
                /* Also may need to check size/value */
                break;
            case COLUMN_QOSWIRELESSTXOPLIM:
                if ( request->requestvb->type != ASN_INTEGER ) {
                    netsnmp_set_request_error( reqinfo, request,
                                               SNMP_ERR_WRONGTYPE );
                    return SNMP_ERR_NOERROR;
                }
                /* Also may need to check size/value */
                break;
            default:
                netsnmp_set_request_error( reqinfo, request,
                                           SNMP_ERR_NOTWRITABLE );
                return SNMP_ERR_NOERROR;
            }
        }
        break;

    case MODE_SET_RESERVE2:
        break;

    case MODE_SET_FREE:
        break;

   case MODE_SET_ACTION:
        for (request=requests; request; request=request->next) {
            table_entry = (struct dot11QosWirelessTable_entry *)
                              netsnmp_extract_iterator_context(request);
            table_info  =     netsnmp_extract_table_info( request);

			if( !table_entry ){
		       	netsnmp_set_request_error(reqinfo,request,SNMP_NOSUCHINSTANCE);
				continue;
		    }   

			void *connection = NULL;
            if(SNMPD_DBUS_ERROR == get_instance_dbus_connection(table_entry->parameter, &connection, SNMPD_INSTANCE_MASTER_V3))
                break;
            
            switch (table_info->colnum) {

			 case COLUMN_QOSWIRELESSAIFS:
			{	
				int result1 = 0,result2 = 0;
				char wtpID[10] = { 0 };
				memset(wtpID,0,10);
				char type[20] = { 0 };
				memset(type,0,20);
				char radioID[10] = { 0 };
				memset(radioID,0,10);
				char cwMin[20] = { 0 };
				char cwMax[20] = { 0 };
				char aifs[20] = { 0 };
				char txopLimit[20] = { 0 };
				char ack[20] = { 0 };
				int radioGId;
				char radio_g_id[10] = { 0 };
				memset(radio_g_id,0,10);
				char qos_name[10] = { 0 };
				memset(qos_name,0,10);
				int ret = 0;
				DCLI_WQOS *WQOS1 = NULL,*WQOS2 = NULL;
				snprintf(wtpID,sizeof(wtpID)-1,"%d",table_entry->WtpID);
				snprintf(radioID,sizeof(radioID)-1,"%d",table_entry->RadioLocalID);

				if(table_entry->QosType == 1)
				{
					memset(type,0,20);
					strncpy(type,"besteffort",sizeof(type)-1);//"BESTEFFORT");
				}
				else if(table_entry->QosType == 2)
				{
					memset(type,0,20);
					strncpy(type,"background",sizeof(type)-1);//BACKGROUND");
				}
				else if(table_entry->QosType == 3)
				{
					memset(type,0,20);
					strncpy(type,"video",sizeof(type)-1);//VIDEO");
				}
				else if(table_entry->QosType == 4)
				{
					memset(type,0,20);
					strncpy(type,"voice",sizeof(type)-1);//VOICE");
				}
				
				result1 = wid_show_qos_radio_cmd(table_entry->parameter, connection,wtpID,radioID,type,&WQOS1);
				if(( 1 == result1 )&&(WQOS1->qos[0])&&(WQOS1->qos[0]->radio_qos[0]))
				{
					memset(cwMin,0,20);
					memset(cwMax,0,20);
					memset(aifs,0,20);
					memset(txopLimit,0,20);
					memset(ack,0,20);
					
					snprintf( cwMin, sizeof(cwMin)-1, "%u", WQOS1->qos[0]->radio_qos[0]->CWMin);
					snprintf( cwMax, sizeof(cwMax)-1, "%u", WQOS1->qos[0]->radio_qos[0]->CWMax);
					snprintf( aifs, sizeof(aifs)-1, "%u", *request->requestvb->val.integer );
					snprintf( txopLimit, sizeof(txopLimit)-1, "%u",WQOS1->qos[0]->radio_qos[0]->TXOPlimit);
					if( 1 == WQOS1->qos[0]->radio_qos[0]->ACK)
					{
						snprintf( ack, sizeof(ack)-1, "ack");
					}
					else
					{
						snprintf( ack, sizeof(ack)-1, "noack");
					}
				
					ret = 0;
					ret = config_radio_qos_service(table_entry->parameter, connection,WQOS1->qos[0]->QosID, type,
										cwMin, cwMax, aifs, txopLimit, ack );	/*返回0表示失败,返回1表示成功,返回-1表示unknown qos type,返回-2表示unknown id format*/
				}
				else
				{
					radioGId = table_entry->WtpID * 4 + table_entry->RadioLocalID;
					snprintf(radio_g_id,sizeof(radio_g_id)-1,"%d",radioGId);
					snprintf(qos_name,sizeof(qos_name)-1,"wqos%d",radioGId);

					create_qos(table_entry->parameter, connection,radio_g_id,qos_name);
					
					ret = 0;
					ret = radio_apply_qos(table_entry->parameter, connection,radioGId,radio_g_id);
					if(ret == 1)
					{
						result2=wid_show_qos_radio_cmd(table_entry->parameter, connection,wtpID,radioID,type,&WQOS2);
						if(( 1 == result2 )&&(WQOS2->qos[0])&&(WQOS2->qos[0]->radio_qos[0]))
						{
							memset(cwMin,0,20);
							memset(cwMax,0,20);
							memset(aifs,0,20);
							memset(txopLimit,0,20);
							memset(ack,0,20);
							
							snprintf( cwMin, sizeof(cwMin)-1, "%u", WQOS2->qos[0]->radio_qos[0]->CWMin);
							snprintf( cwMax, sizeof(cwMax)-1, "%u", WQOS2->qos[0]->radio_qos[0]->CWMax);
							snprintf( aifs, sizeof(aifs)-1, "%u", *request->requestvb->val.integer );
							snprintf( txopLimit, sizeof(txopLimit)-1, "%u",WQOS2->qos[0]->radio_qos[0]->TXOPlimit);
							if( 1 == WQOS2->qos[0]->radio_qos[0]->ACK)
							{
								snprintf( ack, sizeof(ack)-1, "ack");
							}
							else
							{
								snprintf( ack, sizeof(ack)-1, "noack");
							}
						
							ret = 0;
							ret = config_radio_qos_service(table_entry->parameter, connection,WQOS2->qos[0]->QosID, type,
												cwMin, cwMax, aifs, txopLimit, ack );	/*返回0表示失败,返回1表示成功,返回-1表示unknown qos type,返回-2表示unknown id format*/
						}

						if( result2 == 1 )
						{
							Free_qos_one(WQOS2);
						}
					}
				}

				if( 1 != ret )
				{
					netsnmp_set_request_error(reqinfo, requests,SNMP_ERR_WRONGTYPE);
				}

				if( result1 == 1 )
				{
					Free_qos_one(WQOS1);
				}
			}
			 	break;
		    case COLUMN_QOSWIRELESSCWMIN:
			{	
				int result1 = 0,result2 = 0;
				char wtpID[10] = { 0 };
				memset(wtpID,0,10);
				char type[20] = { 0 };
				memset(type,0,20);
				char radioID[10] = { 0 };
				memset(radioID,0,10);
				char cwMin[20] = { 0 };
				char cwMax[20] = { 0 };
				char aifs[20] = { 0 };
				char txopLimit[20] = { 0 };
				char ack[20] = { 0 };
				int radioGId;
				char radio_g_id[10] = { 0 };
				memset(radio_g_id,0,10);
				char qos_name[10] = { 0 };
				memset(qos_name,0,10);
				int ret = 0;
				DCLI_WQOS *WQOS1 = NULL,*WQOS2 = NULL;
				snprintf(wtpID,sizeof(wtpID)-1,"%d",table_entry->WtpID);
				snprintf(radioID,sizeof(radioID)-1,"%d",table_entry->RadioLocalID);

				if(table_entry->QosType == 1)
				{
					memset(type,0,20);
					strncpy(type,"besteffort",sizeof(type)-1);//"BESTEFFORT");
				}
				else if(table_entry->QosType == 2)
				{
					memset(type,0,20);
					strncpy(type,"background",sizeof(type)-1);//BACKGROUND");
				}
				else if(table_entry->QosType == 3)
				{
					memset(type,0,20);
					strncpy(type,"video",sizeof(type)-1);//VIDEO");
				}
				else if(table_entry->QosType == 4)
				{
					memset(type,0,20);
					strncpy(type,"voice",sizeof(type)-1);//VOICE");
				}
				
				result1= wid_show_qos_radio_cmd(table_entry->parameter, connection,wtpID,radioID,type,&WQOS1);				
				if(( 1 == result1 )&&(WQOS1->qos[0])&&(WQOS1->qos[0]->radio_qos[0]))
				{
					memset(cwMin,0,20);
					memset(cwMax,0,20);
					memset(aifs,0,20);
					memset(txopLimit,0,20);
					memset(ack,0,20);
					
					snprintf( cwMin, sizeof(cwMin)-1, "%u", *request->requestvb->val.integer );
					snprintf( cwMax, sizeof(cwMax)-1, "%u", WQOS1->qos[0]->radio_qos[0]->CWMax);
					snprintf( aifs, sizeof(aifs)-1, "%u", WQOS1->qos[0]->radio_qos[0]->AIFS);
					snprintf( txopLimit, sizeof(txopLimit)-1, "%u", WQOS1->qos[0]->radio_qos[0]->TXOPlimit);
					if( 1 == WQOS1->qos[0]->radio_qos[0]->ACK )
					{
						snprintf( ack, sizeof(ack)-1, "ack");
					}
					else
					{
						snprintf( ack, sizeof(ack)-1, "noack");
					}
				
					ret = 0;
					ret = config_radio_qos_service(table_entry->parameter, connection, WQOS1->qos[0]->QosID, type,
										cwMin, cwMax, aifs, txopLimit, ack );	/*返回0表示失败,返回1表示成功,返回-1表示unknown qos type,返回-2表示unknown id format*/
				}
				else
				{
					radioGId = table_entry->WtpID * 4 + table_entry->RadioLocalID;
					snprintf(radio_g_id,sizeof(radio_g_id)-1,"%d",radioGId);
					snprintf(qos_name,sizeof(qos_name)-1,"wqos%d",radioGId);
					create_qos(table_entry->parameter, connection,radio_g_id,qos_name);
					ret = 0;
					ret = radio_apply_qos(table_entry->parameter, connection,radioGId,radio_g_id);
					if(ret == 1)
					{
						result2=wid_show_qos_radio_cmd(table_entry->parameter, connection,wtpID,radioID,type,&WQOS2);
						if(( 1 == result2 )&&(WQOS2->qos[0])&&(WQOS2->qos[0]->radio_qos[0]))
						{
							memset(cwMin,0,20);
							memset(cwMax,0,20);
							memset(aifs,0,20);
							memset(txopLimit,0,20);
							memset(ack,0,20);
							
							snprintf( cwMin, sizeof(cwMin)-1, "%u", *request->requestvb->val.integer );
							snprintf( cwMax, sizeof(cwMax)-1, "%u", WQOS2->qos[0]->radio_qos[0]->CWMax );
							snprintf( aifs, sizeof(aifs)-1, "%u", WQOS2->qos[0]->radio_qos[0]->AIFS );
							snprintf( txopLimit, sizeof(txopLimit)-1, "%u", WQOS2->qos[0]->radio_qos[0]->TXOPlimit);
							if( 1 == WQOS2->qos[0]->radio_qos[0]->ACK )
							{
								snprintf( ack, sizeof(ack)-1, "ack");
							}
							else
							{
								snprintf( ack, sizeof(ack)-1, "noack");
							}
						
							ret = 0;
							ret = config_radio_qos_service(table_entry->parameter, connection, WQOS2->qos[0]->QosID, type,
												cwMin, cwMax, aifs, txopLimit, ack );	/*返回0表示失败,返回1表示成功,返回-1表示unknown qos type,返回-2表示unknown id format*/
						}

						if( result2 == 1 )
						{
							Free_qos_one(WQOS2);
						}
					}
				}

				if( 1 != ret )
				{
					netsnmp_set_request_error(reqinfo, requests,SNMP_ERR_WRONGTYPE);
				}

				if( result1 == 1 )
				{
					Free_qos_one(WQOS1);
				}
			}
				break;
			case COLUMN_QOSWIRELESSCWMAX:
			{	
				int result1=0,result2=0;
				char wtpID[10] = { 0 };
				memset(wtpID,0,10);
				char type[20] = { 0 };
				memset(type,0,20);
				char radioID[10] = { 0 };
				memset(radioID,0,10);
				char cwMin[20] = { 0 };
				char cwMax[20] = { 0 };
				char aifs[20] = { 0 };
				char txopLimit[20] = { 0 };
				char ack[20] = { 0 };
				int radioGId;
				char radio_g_id[10] = { 0 };
				memset(radio_g_id,0,10);
				char qos_name[10] = { 0 };
				memset(qos_name,0,10);
				int ret = 0;
				DCLI_WQOS *WQOS1 = NULL,*WQOS2 = NULL;
				snprintf(wtpID,sizeof(wtpID)-1,"%d",table_entry->WtpID);
				snprintf(radioID,sizeof(radioID)-1,"%d",table_entry->RadioLocalID);
				if(table_entry->QosType == 1)
				{
					memset(type,0,20);
					strncpy(type,"besteffort",sizeof(type)-1);//"BESTEFFORT");
				}
				else if(table_entry->QosType == 2)
				{
					memset(type,0,20);
					strncpy(type,"background",sizeof(type)-1);//BACKGROUND");
				}
				else if(table_entry->QosType == 3)
				{
					memset(type,0,20);
					strncpy(type,"video",sizeof(type)-1);//VIDEO");
				}
				else if(table_entry->QosType == 4)
				{
					memset(type,0,20);
					strncpy(type,"voice",sizeof(type)-1);//VOICE");
				}
				result1 = wid_show_qos_radio_cmd(table_entry->parameter, connection,wtpID,radioID,type,&WQOS1);
				
				if(( 1 == result1 )&&(WQOS1->qos[0])&&(WQOS1->qos[0]->radio_qos[0]))
				{
					memset(cwMin,0,20);
					memset(cwMax,0,20);
					memset(aifs,0,20);
					memset(txopLimit,0,20);
					memset(ack,0,20);
					
					snprintf( cwMin, sizeof(cwMin)-1, "%u", WQOS1->qos[0]->radio_qos[0]->CWMin );
					snprintf( cwMax, sizeof(cwMax)-1, "%u", *request->requestvb->val.integer);
					snprintf( aifs, sizeof(aifs)-1, "%u", WQOS1->qos[0]->radio_qos[0]->AIFS );
					snprintf( txopLimit, sizeof(txopLimit)-1, "%u",WQOS1->qos[0]->radio_qos[0]->TXOPlimit);
					if( 1 == WQOS1->qos[0]->radio_qos[0]->ACK )
					{
						snprintf( ack, sizeof(ack)-1, "ack");
					}
					else
					{
						snprintf( ack, sizeof(ack)-1, "noack");
					}
				
					ret = 0;
					ret = config_radio_qos_service(table_entry->parameter, connection,WQOS1->qos[0]->QosID, type,
										cwMin, cwMax, aifs, txopLimit, ack );	/*返回0表示失败,返回1表示成功,返回-1表示unknown qos type,返回-2表示unknown id format*/
				}
				else
				{
					radioGId = table_entry->WtpID * 4 + table_entry->RadioLocalID;
					snprintf(radio_g_id,sizeof(radio_g_id)-1,"%d",radioGId);
					snprintf(qos_name,sizeof(qos_name)-1,"wqos%d",radioGId);

					create_qos(table_entry->parameter, connection,radio_g_id,qos_name);
					
					ret = 0;
					ret = radio_apply_qos(table_entry->parameter, connection,radioGId,radio_g_id);
					if(ret == 1)
					{
						result2=wid_show_qos_radio_cmd(table_entry->parameter, connection,wtpID,radioID,type,&WQOS2);
						if(( 1 == result2 )&&(WQOS2->qos[0])&&(WQOS2->qos[0]->radio_qos[0]))
						{
							memset(cwMin,0,20);
							memset(cwMax,0,20);
							memset(aifs,0,20);
							memset(txopLimit,0,20);
							memset(ack,0,20);
							
							snprintf( cwMin, sizeof(cwMin)-1, "%u", WQOS2->qos[0]->radio_qos[0]->CWMin );
							snprintf( cwMax, sizeof(cwMax)-1, "%u", *request->requestvb->val.integer);
							snprintf( aifs, sizeof(aifs)-1, "%u", WQOS2->qos[0]->radio_qos[0]->AIFS );
							snprintf( txopLimit, sizeof(txopLimit)-1, "%u",WQOS2->qos[0]->radio_qos[0]->TXOPlimit);
							if( 1 == WQOS2->qos[0]->radio_qos[0]->ACK )
							{
								snprintf( ack, sizeof(ack)-1, "ack");
							}
							else
							{
								snprintf( ack, sizeof(ack)-1, "noack");
							}
						
							ret = 0;
							ret = config_radio_qos_service(table_entry->parameter, connection,WQOS2->qos[0]->QosID, type,
												cwMin, cwMax, aifs, txopLimit, ack );	/*返回0表示失败,返回1表示成功,返回-1表示unknown qos type,返回-2表示unknown id format*/
						}

						if( result2 == 1 )
						{
							Free_qos_one(WQOS2);
						}
					}
				}

				if( 1 != ret )
				{
					netsnmp_set_request_error(reqinfo, requests,SNMP_ERR_WRONGTYPE);
				}


				if( result1 == 1 )
				{
					Free_qos_one(WQOS1);
				}
			}
				break;
			case COLUMN_QOSWIRELESSTXOPLIM:
			{	
				int result1 = 0,result2 = 0;
				char wtpID[10] = { 0 };
				memset(wtpID,0,10);
				char type[20] = { 0 };
				memset(type,0,20);
				char radioID[10] = { 0 };
				memset(radioID,0,10);
				char cwMin[20] = { 0 };
				char cwMax[20] = { 0 };
				char aifs[20] = { 0 };
				char txopLimit[20] = { 0 };
				char ack[20] = { 0 };
				int radioGId;
				char radio_g_id[10] = { 0 };
				memset(radio_g_id,0,10);
				char qos_name[10] = { 0 };
				memset(qos_name,0,10);
				int ret = 0;
				DCLI_WQOS *WQOS1 = NULL,*WQOS2 = NULL;
				snprintf(wtpID,sizeof(wtpID)-1,"%d",table_entry->WtpID);
				snprintf(radioID,sizeof(radioID)-1,"%d",table_entry->RadioLocalID);

				if(table_entry->QosType == 1)
				{
					memset(type,0,20);
					strncpy(type,"besteffort",sizeof(type)-1);//"BESTEFFORT");
				}
				else if(table_entry->QosType == 2)
				{
					memset(type,0,20);
					strncpy(type,"background",sizeof(type)-1);//BACKGROUND");
				}
				else if(table_entry->QosType == 3)
				{
					memset(type,0,20);
					strncpy(type,"video",sizeof(type)-1);//VIDEO");
				}
				else if(table_entry->QosType == 4)
				{
					memset(type,0,20);
					strncpy(type,"voice",sizeof(type)-1);//VOICE");
				}
				
				result1= wid_show_qos_radio_cmd(table_entry->parameter, connection,wtpID,radioID,type,&WQOS1);				
				if(( 1 == result1 )&&(WQOS1->qos[0])&&(WQOS1->qos[0]->radio_qos[0]))
				{
					memset(cwMin,0,20);
					memset(cwMax,0,20);
					memset(aifs,0,20);
					memset(txopLimit,0,20);
					memset(ack,0,20);
					
					snprintf( cwMin, sizeof(cwMin)-1, "%u", WQOS1->qos[0]->radio_qos[0]->CWMin );
					snprintf( cwMax, sizeof(cwMax)-1, "%u", WQOS1->qos[0]->radio_qos[0]->CWMax );
					snprintf( aifs, sizeof(aifs)-1, "%u", WQOS1->qos[0]->radio_qos[0]->AIFS );
					snprintf( txopLimit, sizeof(txopLimit)-1, "%u", *request->requestvb->val.integer);
					if( 1 == WQOS1->qos[0]->radio_qos[0]->ACK )
					{
						snprintf( ack, sizeof(ack)-1, "ack");
					}
					else
					{
						snprintf( ack, sizeof(ack)-1, "noack");
					}

					ret = 0;				
					ret = config_radio_qos_service(table_entry->parameter, connection, WQOS1->qos[0]->QosID, type,
										cwMin, cwMax, aifs, txopLimit, ack );	/*返回0表示失败,返回1表示成功,返回-1表示unknown qos type,返回-2表示unknown id format*/

				}
				else
				{
					radioGId = table_entry->WtpID * 4 + table_entry->RadioLocalID;
					snprintf(radio_g_id,sizeof(radio_g_id)-1,"%d",radioGId);
					snprintf(qos_name,sizeof(qos_name)-1,"wqos%d",radioGId);

					create_qos(table_entry->parameter, connection,radio_g_id,qos_name);
					
					ret = 0;
					ret = radio_apply_qos(table_entry->parameter, connection,radioGId,radio_g_id);
					if(ret == 1)
					{
						result2=wid_show_qos_radio_cmd(table_entry->parameter, connection,wtpID,radioID,type,&WQOS2);
						if(( 1 == result2 )&&(WQOS2->qos[0])&&(WQOS2->qos[0]->radio_qos[0]))
						{
							memset(cwMin,0,20);
							memset(cwMax,0,20);
							memset(aifs,0,20);
							memset(txopLimit,0,20);
							memset(ack,0,20);
							
							snprintf( cwMin, sizeof(cwMin)-1, "%u", WQOS2->qos[0]->radio_qos[0]->CWMin );
							snprintf( cwMax, sizeof(cwMax)-1, "%u", WQOS2->qos[0]->radio_qos[0]->CWMax );
							snprintf( aifs, sizeof(aifs)-1, "%u", WQOS2->qos[0]->radio_qos[0]->AIFS );
							snprintf( txopLimit, sizeof(txopLimit)-1, "%u", *request->requestvb->val.integer);
							if( 1 == WQOS2->qos[0]->radio_qos[0]->ACK )
							{
								snprintf( ack, sizeof(ack)-1, "ack");
							}
							else
							{
								snprintf( ack, sizeof(ack)-1, "noack");
							}
						
							ret = 0;
							ret = config_radio_qos_service(table_entry->parameter, connection, WQOS2->qos[0]->QosID, type,
												cwMin, cwMax, aifs, txopLimit, ack );	/*返回0表示失败,返回1表示成功,返回-1表示unknown qos type,返回-2表示unknown id format*/
						
						}

						if( result2 == 1 )
						{
							Free_qos_one(WQOS2);
						}
					}
				}

				if( 1 != ret )
				{
					netsnmp_set_request_error(reqinfo, requests,SNMP_ERR_WRONGTYPE);
				}

				if( result1 == 1 )
				{
					Free_qos_one(WQOS1);
				}
			}
			break;
            }
        }
        break;

    case MODE_SET_UNDO:
        for (request=requests; request; request=request->next) {
            table_entry = (struct dot11QosWirelessTable_entry *)
                              netsnmp_extract_iterator_context(request);
            table_info  =     netsnmp_extract_table_info(      request);
    
            switch (table_info->colnum) {
            case COLUMN_QOSWIRELESSAIFS:
                /* Need to restore old 'table_entry->QosWirelessAIFS' value.
                   May need to use 'memcpy' */
                break;
            case COLUMN_QOSWIRELESSCWMIN:
                /* Need to restore old 'table_entry->QosWirelessCWmin' value.
                   May need to use 'memcpy' */
                break;
            case COLUMN_QOSWIRELESSCWMAX:
                /* Need to restore old 'table_entry->QoSWirelessCWmax' value.
                   May need to use 'memcpy' */
                break;
            case COLUMN_QOSWIRELESSTXOPLIM:
                /* Need to restore old 'table_entry->QoSWirelessTXOPLim' value.
                   May need to use 'memcpy' */
                break;
            }
        }
        break;

    case MODE_SET_COMMIT:
        break;
    }
    return SNMP_ERR_NOERROR;
}
/* neIeee8021QBridgeVlanCurrentTable table mapper */
int
neIeee8021QBridgeVlanCurrentTable_mapper (
	netsnmp_mib_handler *handler,
	netsnmp_handler_registration *reginfo,
	netsnmp_agent_request_info *reqinfo,
	netsnmp_request_info *requests)
{
	netsnmp_request_info *request;
	netsnmp_table_request_info *table_info;
	neIeee8021QBridgeVlanCurrentEntry_t *table_entry;
	register ieee8021QBridgeVlanCurrentEntry_t *poEntry = NULL;
	void *pvOldDdata = NULL;
	int ret;
	
	switch (reqinfo->mode)
	{
	/*
	 * Read-support (also covers GetNext requests)
	 */
	case MODE_GET:
		for (request = requests; request != NULL; request = request->next)
		{
			poEntry = (ieee8021QBridgeVlanCurrentEntry_t*) netsnmp_extract_iterator_context (request);
			table_info = netsnmp_extract_table_info (request);
			if (poEntry == NULL)
			{
				netsnmp_set_request_error (reqinfo, request, SNMP_NOSUCHINSTANCE);
				continue;
			}
			table_entry = &poEntry->oNe;
			
			switch (table_info->colnum)
			{
			case NEIEEE8021QBRIDGEVLANCURRENTADMINFLAGS:
				snmp_set_var_typed_value (request->requestvb, ASN_OCTET_STR, (u_char*) table_entry->au8AdminFlags, table_entry->u16AdminFlags_len);
				break;
			case NEIEEE8021QBRIDGEVLANCURRENTOPERSTATE:
				snmp_set_var_typed_integer (request->requestvb, ASN_INTEGER, table_entry->i32OperState);
				break;
			case NEIEEE8021QBRIDGEVLANCURRENTLEARNT:
				snmp_set_var_typed_value (request->requestvb, ASN_OCTET_STR, (u_char*) table_entry->pu8Learnt, table_entry->u16Learnt_len);
				break;
			case NEIEEE8021QBRIDGEVLANCURRENTIFINDEX:
				snmp_set_var_typed_integer (request->requestvb, ASN_INTEGER, table_entry->u32IfIndex);
				break;
				
			default:
				netsnmp_set_request_error (reqinfo, request, SNMP_NOSUCHOBJECT);
				break;
			}
		}
		break;
		
	/*
	 * Write-support
	 */
	case MODE_SET_RESERVE1:
		for (request = requests; request != NULL; request = request->next)
		{
			poEntry = (ieee8021QBridgeVlanCurrentEntry_t*) netsnmp_extract_iterator_context (request);
			table_info = netsnmp_extract_table_info (request);
			table_entry = &poEntry->oNe;
			
			switch (table_info->colnum)
			{
			case NEIEEE8021QBRIDGEVLANCURRENTADMINFLAGS:
				ret = netsnmp_check_vb_type_and_max_size (request->requestvb, ASN_OCTET_STR, sizeof (table_entry->au8AdminFlags));
				if (ret != SNMP_ERR_NOERROR)
				{
					netsnmp_set_request_error (reqinfo, request, ret);
					return SNMP_ERR_NOERROR;
				}
				break;
				
			default:
				netsnmp_set_request_error (reqinfo, request, SNMP_ERR_NOTWRITABLE);
				return SNMP_ERR_NOERROR;
			}
		}
		break;
		
	case MODE_SET_RESERVE2:
		for (request = requests; request != NULL; request = request->next)
		{
			poEntry = (ieee8021QBridgeVlanCurrentEntry_t*) netsnmp_extract_iterator_context (request);
			table_info = netsnmp_extract_table_info (request);
			if (poEntry == NULL)
			{
				netsnmp_set_request_error (reqinfo, request, SNMP_NOSUCHINSTANCE);
				continue;
			}
			table_entry = &poEntry->oNe;
			
			switch (table_info->colnum)
			{
			case NEIEEE8021QBRIDGEVLANCURRENTADMINFLAGS:
				if (poEntry->u8RowStatus == xRowStatus_active_c || poEntry->u8RowStatus == xRowStatus_notReady_c)
				{
					netsnmp_set_request_error (reqinfo, request, SNMP_ERR_RESOURCEUNAVAILABLE);
					return SNMP_ERR_NOERROR;
				}
				break;
			}
		}
		break;
		
	case MODE_SET_FREE:
		break;
		
	case MODE_SET_ACTION:
		for (request = requests; request != NULL; request = request->next)
		{
			pvOldDdata = netsnmp_request_get_list_data (request, ROLLBACK_BUFFER);
			poEntry = (ieee8021QBridgeVlanCurrentEntry_t*) netsnmp_extract_iterator_context (request);
			table_info = netsnmp_extract_table_info (request);
			table_entry = &poEntry->oNe;
			
			switch (table_info->colnum)
			{
			case NEIEEE8021QBRIDGEVLANCURRENTADMINFLAGS:
				if (pvOldDdata == NULL && (pvOldDdata = xBuffer_cAlloc (sizeof (xOctetString_t) + sizeof (table_entry->au8AdminFlags))) == NULL)
				{
					netsnmp_set_request_error (reqinfo, request, SNMP_ERR_RESOURCEUNAVAILABLE);
					return SNMP_ERR_NOERROR;
				}
				else if (pvOldDdata != table_entry)
				{
					((xOctetString_t*) pvOldDdata)->pData = pvOldDdata + sizeof (xOctetString_t);
					((xOctetString_t*) pvOldDdata)->u16Len = table_entry->u16AdminFlags_len;
					memcpy (((xOctetString_t*) pvOldDdata)->pData, table_entry->au8AdminFlags, sizeof (table_entry->au8AdminFlags));
					netsnmp_request_add_list_data (request, netsnmp_create_data_list (ROLLBACK_BUFFER, pvOldDdata, &xBuffer_free));
				}
				
				memset (table_entry->au8AdminFlags, 0, sizeof (table_entry->au8AdminFlags));
				memcpy (table_entry->au8AdminFlags, request->requestvb->val.string, request->requestvb->val_len);
				table_entry->u16AdminFlags_len = request->requestvb->val_len;
				break;
			}
		}
		break;
		
	case MODE_SET_UNDO:
		for (request = requests; request != NULL; request = request->next)
		{
			pvOldDdata = netsnmp_request_get_list_data (request, ROLLBACK_BUFFER);
			poEntry = (ieee8021QBridgeVlanCurrentEntry_t*) netsnmp_extract_iterator_context (request);
			table_info = netsnmp_extract_table_info (request);
			if (poEntry == NULL || pvOldDdata == NULL)
			{
				continue;
			}
			table_entry = &poEntry->oNe;
			
			switch (table_info->colnum)
			{
			case NEIEEE8021QBRIDGEVLANCURRENTADMINFLAGS:
				memcpy (table_entry->au8AdminFlags, ((xOctetString_t*) pvOldDdata)->pData, ((xOctetString_t*) pvOldDdata)->u16Len);
				table_entry->u16AdminFlags_len = ((xOctetString_t*) pvOldDdata)->u16Len;
				break;
			}
		}
		break;
		
	case MODE_SET_COMMIT:
		break;
	}
	
	return SNMP_ERR_NOERROR;
}
/** handles requests for the dot11VlanAbilityTable table */
int
dot11VlanAbilityTable_handler(
    netsnmp_mib_handler               *handler,
    netsnmp_handler_registration      *reginfo,
    netsnmp_agent_request_info        *reqinfo,
    netsnmp_request_info              *requests) 
{

	netsnmp_request_info       *request;
	netsnmp_table_request_info *table_info;
	struct dot11VlanAbilityTable_entry          *table_entry;

	switch (reqinfo->mode) 
	{
		/*
		* Read-support (also covers GetNext requests)
		*/
		case MODE_GET:
		{
			for (request=requests; request; request=request->next) 
			{
				table_entry = (struct dot11VlanAbilityTable_entry *)
				netsnmp_extract_iterator_context(request);
				table_info  =     netsnmp_extract_table_info(request);


				if( !table_entry )
				{
					netsnmp_set_request_error(reqinfo,request,SNMP_NOSUCHINSTANCE);
					continue;
				}     

				switch (table_info->colnum) 
				{
					case COLUMN_VLANID:
					{
						snmp_set_var_typed_value( request->requestvb, ASN_INTEGER,
						(u_char*)&table_entry->vlanID,
						sizeof(long));
					
						break;
					}
					case COLUMN_PRIORITY:
					{
						snmp_set_var_typed_value( request->requestvb, ASN_INTEGER,
						(u_char*)&table_entry->Priority,
						sizeof(long));
					
						break;
					}
				default:
				                netsnmp_set_request_error( reqinfo, request,
				                                           SNMP_ERR_NOTWRITABLE );
				                return SNMP_ERR_NOERROR;	
				}
			}
		}
		break;

		/*
		* Write-support
		*/
		case MODE_SET_RESERVE1:
		{
			for (request=requests; request; request=request->next) 
			{
				table_entry = (struct dot11VlanAbilityTable_entry *)
				netsnmp_extract_iterator_context(request);
				table_info  =     netsnmp_extract_table_info(request);

				switch (table_info->colnum) 
				{
					case COLUMN_VLANID:
					{
						if ( request->requestvb->type != ASN_INTEGER ) 
						{
							netsnmp_set_request_error( reqinfo, request,SNMP_ERR_WRONGTYPE );
							return SNMP_ERR_NOERROR;
						}
					}
					/* Also may need to check size/value */
					break;

					case COLUMN_PRIORITY:
					{
						if ( request->requestvb->type != ASN_INTEGER ) 
						{
							netsnmp_set_request_error( reqinfo, request,SNMP_ERR_WRONGTYPE );
							return SNMP_ERR_NOERROR;
						}
					}
					/* Also may need to check size/value */
					break;

					
					default:
					netsnmp_set_request_error( reqinfo, request,SNMP_ERR_NOTWRITABLE );
					return SNMP_ERR_NOERROR;
				}
			}
		}
		break;

		case MODE_SET_RESERVE2:
		break;

		case MODE_SET_FREE:
		break;

		case MODE_SET_ACTION:
		{
			for (request=requests; request; request=request->next) 
			{
				table_entry = (struct dot11VlanAbilityTable_entry *)
				netsnmp_extract_iterator_context(request);
				table_info  =     netsnmp_extract_table_info(      request);

				if( !table_entry )
				{
					netsnmp_set_request_error(reqinfo,request,SNMP_NOSUCHINSTANCE);
					continue;
				}  
				switch (table_info->colnum) 
				{
					case COLUMN_VLANID:
					{
                        void *connection = NULL;
                        if(SNMPD_DBUS_ERROR == get_instance_dbus_connection(table_entry->parameter, &connection, SNMPD_INSTANCE_MASTER_V3))
                            return MFD_ERROR;
        
						int ret1=0,ret2=0;
						char vlanid[10] = { 0 };
						memset(vlanid,0,10);
						/* Need to save old 'table_entry->vlanID' value.
						May need to use 'memcpy' */
						//table_entry->old_vlanID = table_entry->vlanID;
						table_entry->vlanID     = *request->requestvb->val.integer;
						ret1=config_wlan_service(table_entry->parameter, connection,table_entry->local_wlanCurrID,"disable");
						if(ret1!=1)
						{	
						    if(SNMPD_CONNECTION_ERROR == ret1) {
                                close_slot_dbus_connection(table_entry->parameter.slot_id);
                    	    }
							netsnmp_set_request_error(reqinfo,request,SNMP_ERR_WRONGTYPE);
							break;
						}
						
						snprintf(vlanid,sizeof(vlanid)-1,"%d",table_entry->vlanID);
						ret2=set_wlan_vlan_id(table_entry->parameter, connection,table_entry->local_wlanCurrID,vlanid);
						if(ret2!=1)
						{	
						    if(SNMPD_CONNECTION_ERROR == ret2) {
                                close_slot_dbus_connection(table_entry->parameter.slot_id);
                    	    }
							netsnmp_set_request_error(reqinfo,request,SNMP_ERR_WRONGTYPE);
						}						
					}
					break;

					case COLUMN_PRIORITY:
					{
                        void *connection = NULL;
                        if(SNMPD_DBUS_ERROR == get_instance_dbus_connection(table_entry->parameter, &connection, SNMPD_INSTANCE_MASTER_V3))
                            return MFD_ERROR;
                            
						int ret1=0,ret2=0;
						char pro[10] = { 0 };
						memset(pro,0,10);
						/* Need to save old 'table_entry->Priority' value.
						May need to use 'memcpy' */
						//table_entry->old_Priority = table_entry->Priority;
						table_entry->Priority = *request->requestvb->val.integer;
						ret1=config_wlan_service(table_entry->parameter, connection,table_entry->local_wlanCurrID,"disable");
						if(ret1!=1)
						{	
						    if(SNMPD_CONNECTION_ERROR == ret1) {
                                close_slot_dbus_connection(table_entry->parameter.slot_id);
                    	    }
							netsnmp_set_request_error(reqinfo,request,SNMP_ERR_WRONGTYPE);
							break;
						}
						
						snprintf(pro,sizeof(pro)-1,"%d",table_entry->Priority);
						ret2=set_wlan_vlan_priority(table_entry->parameter, connection,table_entry->local_wlanCurrID,pro);
						if(ret2!=1)
						{	
						    if(SNMPD_CONNECTION_ERROR == ret2) {
                                close_slot_dbus_connection(table_entry->parameter.slot_id);
                    	    }
							netsnmp_set_request_error(reqinfo,request,SNMP_ERR_WRONGTYPE);
						}
					}
					break;

				}
			}
		}
		break;

		case MODE_SET_UNDO:
		{
			for (request=requests; request; request=request->next) 
			{
				table_entry = (struct dot11VlanAbilityTable_entry *)
				netsnmp_extract_iterator_context(request);
				table_info  =     netsnmp_extract_table_info(request);

				switch (table_info->colnum) 
				{
					case COLUMN_VLANID:
					{
						/* Need to restore old 'table_entry->vlanID' value.
						May need to use 'memcpy' */
						//  table_entry->vlanID = table_entry->old_vlanID;
					}
					break;

					case COLUMN_PRIORITY:
					{
						/* Need to restore old 'table_entry->Priority' value.
						May need to use 'memcpy' */
						//  table_entry->Priority = table_entry->old_Priority;
					}
					break;
				}
			}
		}
		break;

		case MODE_SET_COMMIT:
		break;
	}
return SNMP_ERR_NOERROR;
}
Exemple #19
0
/** handles requests for the cpqSasPhyDrvTable table */
int
cpqSasPhyDrvTable_handler(netsnmp_mib_handler *handler,
                          netsnmp_handler_registration *reginfo,
                          netsnmp_agent_request_info *reqinfo,
                          netsnmp_request_info *requests)
{

    netsnmp_request_info *request;
    netsnmp_table_request_info *table_info;
    cpqSasPhyDrvTable_entry *table_entry;

    DEBUGMSGTL(("cpqSasPhyDrvTable:handler", "Processing request (%d)\n",
                reqinfo->mode));

    switch (reqinfo->mode) {
        /*
         * Read-support (also covers GetNext requests)
         */
    case MODE_GET:
        for (request = requests; request; request = request->next) {
            if (request->processed)
                continue;
            table_entry = (cpqSasPhyDrvTable_entry *)
                netsnmp_container_table_extract_context(request);
            table_info = netsnmp_extract_table_info(request);
            if ((NULL == table_entry) || (NULL == table_info)) {
                snmp_log(LOG_ERR,
                         "could not extract table entry or info for cpqSasPhyDrvTable\n");
                snmp_set_var_typed_value(request->requestvb,
                                         SNMP_ERR_GENERR, NULL, 0);
                continue;
            }

            switch (table_info->colnum) {
            case COLUMN_CPQSASPHYDRVHBAINDEX:
                if (!table_entry) {
                    netsnmp_set_request_error(reqinfo, request,
                                              SNMP_NOSUCHINSTANCE);
                    continue;
                }
                snmp_set_var_typed_integer(request->requestvb, ASN_INTEGER,
                                           table_entry->
                                           cpqSasPhyDrvHbaIndex);
                break;
            case COLUMN_CPQSASPHYDRVINDEX:
                if (!table_entry) {
                    netsnmp_set_request_error(reqinfo, request,
                                              SNMP_NOSUCHINSTANCE);
                    continue;
                }
                snmp_set_var_typed_integer(request->requestvb, ASN_INTEGER,
                                           table_entry->cpqSasPhyDrvIndex);
                break;
            case COLUMN_CPQSASPHYDRVLOCATIONSTRING:
                if (!table_entry) {
                    netsnmp_set_request_error(reqinfo, request,
                                              SNMP_NOSUCHINSTANCE);
                    continue;
                }
                snmp_set_var_typed_value(request->requestvb, ASN_OCTET_STR,
                                         table_entry->
                                         cpqSasPhyDrvLocationString,
                                         table_entry->
                                         cpqSasPhyDrvLocationString_len);
                break;
            case COLUMN_CPQSASPHYDRVMODEL:
                if (!table_entry) {
                    netsnmp_set_request_error(reqinfo, request,
                                              SNMP_NOSUCHINSTANCE);
                    continue;
                }
                snmp_set_var_typed_value(request->requestvb, ASN_OCTET_STR,
                                         table_entry->cpqSasPhyDrvModel,
                                         table_entry->
                                         cpqSasPhyDrvModel_len);
                break;
            case COLUMN_CPQSASPHYDRVSTATUS:
                if (!table_entry) {
                    netsnmp_set_request_error(reqinfo, request,
                                              SNMP_NOSUCHINSTANCE);
                    continue;
                }
                snmp_set_var_typed_integer(request->requestvb, ASN_INTEGER,
                                           table_entry->
                                           cpqSasPhyDrvStatus);
                break;
            case COLUMN_CPQSASPHYDRVCONDITION:
                if (!table_entry) {
                    netsnmp_set_request_error(reqinfo, request,
                                              SNMP_NOSUCHINSTANCE);
                    continue;
                }
                snmp_set_var_typed_integer(request->requestvb, ASN_INTEGER,
                                           table_entry->
                                           cpqSasPhyDrvCondition);
                break;
            case COLUMN_CPQSASPHYDRVFWREV:
                if (!table_entry) {
                    netsnmp_set_request_error(reqinfo, request,
                                              SNMP_NOSUCHINSTANCE);
                    continue;
                }
                snmp_set_var_typed_value(request->requestvb, ASN_OCTET_STR,
                                         table_entry->cpqSasPhyDrvFWRev,
                                         table_entry->
                                         cpqSasPhyDrvFWRev_len);
                break;
            case COLUMN_CPQSASPHYDRVSIZE:
                if (!table_entry) {
                    netsnmp_set_request_error(reqinfo, request,
                                              SNMP_NOSUCHINSTANCE);
                    continue;
                }
                snmp_set_var_typed_integer(request->requestvb, ASN_INTEGER,
                                           table_entry->cpqSasPhyDrvSize);
                break;
            case COLUMN_CPQSASPHYDRVUSEDREALLOCS:
                if (!table_entry) {
                    netsnmp_set_request_error(reqinfo, request,
                                              SNMP_NOSUCHINSTANCE);
                    continue;
                }
                snmp_set_var_typed_integer(request->requestvb, ASN_COUNTER,
                                           table_entry->
                                           cpqSasPhyDrvUsedReallocs);
                break;
            case COLUMN_CPQSASPHYDRVSERIALNUMBER:
                if (!table_entry) {
                    netsnmp_set_request_error(reqinfo, request,
                                              SNMP_NOSUCHINSTANCE);
                    continue;
                }
                snmp_set_var_typed_value(request->requestvb, ASN_OCTET_STR,
                                         table_entry->
                                         cpqSasPhyDrvSerialNumber,
                                         table_entry->
                                         cpqSasPhyDrvSerialNumber_len);
                break;
            case COLUMN_CPQSASPHYDRVMEMBERLOGDRV:
                if (!table_entry) {
                    netsnmp_set_request_error(reqinfo, request,
                                              SNMP_NOSUCHINSTANCE);
                    continue;
                }
                snmp_set_var_typed_integer(request->requestvb, ASN_INTEGER,
                                           table_entry->
                                           cpqSasPhyDrvMemberLogDrv);
                break;
            case COLUMN_CPQSASPHYDRVROTATIONALSPEED:
                if (!table_entry) {
                    netsnmp_set_request_error(reqinfo, request,
                                              SNMP_NOSUCHINSTANCE);
                    continue;
                }
                snmp_set_var_typed_integer(request->requestvb, ASN_INTEGER,
                                           table_entry->
                                           cpqSasPhyDrvRotationalSpeed);
                break;
            case COLUMN_CPQSASPHYDRVOSNAME:
                if (!table_entry) {
                    netsnmp_set_request_error(reqinfo, request,
                                              SNMP_NOSUCHINSTANCE);
                    continue;
                }
                snmp_set_var_typed_value(request->requestvb, ASN_OCTET_STR,
                                         table_entry->cpqSasPhyDrvOsName,
                                         table_entry->
                                         cpqSasPhyDrvOsName_len);
                break;
            case COLUMN_CPQSASPHYDRVPLACEMENT:
                if (!table_entry) {
                    netsnmp_set_request_error(reqinfo, request,
                                              SNMP_NOSUCHINSTANCE);
                    continue;
                }
                snmp_set_var_typed_integer(request->requestvb, ASN_INTEGER,
                                           table_entry->
                                           cpqSasPhyDrvPlacement);
                break;
            case COLUMN_CPQSASPHYDRVHOTPLUG:
                if (!table_entry) {
                    netsnmp_set_request_error(reqinfo, request,
                                              SNMP_NOSUCHINSTANCE);
                    continue;
                }
                snmp_set_var_typed_integer(request->requestvb, ASN_INTEGER,
                                           table_entry->
                                           cpqSasPhyDrvHotPlug);
                break;
            case COLUMN_CPQSASPHYDRVTYPE:
                if (!table_entry) {
                    netsnmp_set_request_error(reqinfo, request,
                                              SNMP_NOSUCHINSTANCE);
                    continue;
                }
                snmp_set_var_typed_integer(request->requestvb, ASN_INTEGER,
                                           table_entry->cpqSasPhyDrvType);
                break;
            case COLUMN_CPQSASPHYDRVSASADDRESS:
                if (!table_entry) {
                    netsnmp_set_request_error(reqinfo, request,
                                              SNMP_NOSUCHINSTANCE);
                    continue;
                }
                snmp_set_var_typed_value(request->requestvb, ASN_OCTET_STR,
                                         table_entry->
                                         cpqSasPhyDrvSasAddress,
                                         table_entry->
                                         cpqSasPhyDrvSasAddress_len);
                break;
            case COLUMN_CPQSASPHYDRVMEDIATYPE:
                if (!table_entry) {
                    netsnmp_set_request_error(reqinfo, request,
                                              SNMP_NOSUCHINSTANCE);
                    continue;
                }
                snmp_set_var_typed_integer(request->requestvb, ASN_INTEGER,
                                           table_entry->cpqSasPhyDrvMediaType);
                break;
            case COLUMN_CPQSASPHYDRVSSDWEARSTATUS:
                if (!table_entry) {
                    netsnmp_set_request_error(reqinfo, request,
                                              SNMP_NOSUCHINSTANCE);
                    continue;
                }
                snmp_set_var_typed_integer(request->requestvb, ASN_INTEGER,
                                           table_entry->cpqSasPhyDrvSSDWearStatus);
                break;

            case COLUMN_CPQSASPHYDRVPOWERONHOURS:
                if (!table_entry) {
                    netsnmp_set_request_error(reqinfo, request,
                                              SNMP_NOSUCHINSTANCE);
                    continue;
                }
                snmp_set_var_typed_integer(request->requestvb, ASN_COUNTER,
                                           table_entry->cpqSasPhyDrvPowerOnHours);
                break;

            case COLUMN_CPQSASPHYDRVSSDPERCNTENDRNCEUSED:
                if (!table_entry) {
                    netsnmp_set_request_error(reqinfo, request,
                                              SNMP_NOSUCHINSTANCE);
                    continue;
                }
                snmp_set_var_typed_integer(request->requestvb, ASN_GAUGE,
                                           table_entry->cpqSasPhyDrvSSDPercntEndrnceUsed);
                break;

            case COLUMN_CPQSASPHYDRVSSDESTTIMEREMAININGHOURS:
                if (!table_entry) {
                    netsnmp_set_request_error(reqinfo, request,
                                              SNMP_NOSUCHINSTANCE);
                    continue;
                }
                snmp_set_var_typed_integer(request->requestvb, ASN_COUNTER,
                                           table_entry->cpqSasPhyDrvSSDEstTimeRemainingHours);
                break;

            case COLUMN_CPQSASPHYDRVAUTHENTICATIONSTATUS:
                if (!table_entry) {
                    netsnmp_set_request_error(reqinfo, request,
                                              SNMP_NOSUCHINSTANCE);
                    continue;
                }
                snmp_set_var_typed_integer(request->requestvb, ASN_INTEGER,
                                           table_entry->cpqSasPhyDrvAuthenticationStatus);
                break;

            case COLUMN_CPQSASPHYDRVSMARTCARRIERAPPFWREV:
                if (!table_entry) {
                    netsnmp_set_request_error(reqinfo, request,
                                              SNMP_NOSUCHINSTANCE);
                    continue;
                }
                snmp_set_var_typed_integer(request->requestvb, ASN_INTEGER,
                                           table_entry->cpqSasPhyDrvSmartCarrierAppFWRev);
                break;

            case COLUMN_CPQSASPHYDRVSMARTCARRIERBOOTLDRFWREV:
                if (!table_entry) {
                    netsnmp_set_request_error(reqinfo, request,
                                              SNMP_NOSUCHINSTANCE);
                    continue;
                }
                snmp_set_var_typed_integer(request->requestvb, ASN_INTEGER,
                                           table_entry->cpqSasPhyDrvSmartCarrierAppFWRev);
                break;

            case COLUMN_CPQSASPHYDRVCURRTEMPERATURE:
                if (!table_entry) {
                    netsnmp_set_request_error(reqinfo, request,
                                              SNMP_NOSUCHINSTANCE);
                    continue;
                }
                snmp_set_var_typed_integer(request->requestvb, ASN_GAUGE,
                                           table_entry->cpqSasPhyDrvCurrTemperature);
                break;

            case COLUMN_CPQSASPHYDRVTEMPERATURETHRESHOLD:
                if (!table_entry) {
                    netsnmp_set_request_error(reqinfo, request,
                                              SNMP_NOSUCHINSTANCE);
                    continue;
                }
                snmp_set_var_typed_integer(request->requestvb, ASN_GAUGE,
                                           table_entry->cpqSasPhyDrvTemperatureThreshold);
                break;


            default:
                netsnmp_set_request_error(reqinfo, request,
                                          SNMP_NOSUCHOBJECT);
                break;
            }
        }
        break;

    }
    return SNMP_ERR_NOERROR;
}
/** handles requests for the nsVacmAccessTable table */
int
nsVacmAccessTable_handler(netsnmp_mib_handler *handler,
                          netsnmp_handler_registration *reginfo,
                          netsnmp_agent_request_info *reqinfo,
                          netsnmp_request_info *requests)
{

    netsnmp_request_info *request;
    netsnmp_table_request_info *table_info;
    netsnmp_variable_list      *idx;
    struct vacm_accessEntry    *entry;
    char atype[20];
    int  viewIdx, ret;
    char *gName, *cPrefix;
    int  model, level;

    switch (reqinfo->mode) {
        /*
         * Read-support (also covers GetNext requests)
         */
    case MODE_GET:
        for (request = requests; request; request = request->next) {
            entry = (struct vacm_accessEntry *)
                netsnmp_extract_iterator_context(request);
            table_info = netsnmp_extract_table_info(request);

            /* Extract the authType token from the list of indexes */
            idx = table_info->indexes->next_variable->next_variable->next_variable->next_variable;
            memset(atype, 0, sizeof(atype));
            memcpy(atype, (char *)idx->val.string, idx->val_len);
            viewIdx = se_find_value_in_slist(VACM_VIEW_ENUM_NAME, atype);
            DEBUGMSGTL(("nsVacm", "GET %s (%d)\n", idx->val.string, viewIdx));

            if (!entry || viewIdx < 0)
                continue;

            switch (table_info->colnum) {
            case COLUMN_NSVACMCONTEXTMATCH:
                snmp_set_var_typed_integer(request->requestvb, ASN_INTEGER,
                                           entry->contextMatch);
                break;
            case COLUMN_NSVACMVIEWNAME:
                snmp_set_var_typed_value(request->requestvb, ASN_OCTET_STR,
                               (u_char *)entry->views[ viewIdx ],
                                  strlen(entry->views[ viewIdx ]));
                break;
            case COLUMN_VACMACCESSSTORAGETYPE:
                snmp_set_var_typed_integer(request->requestvb, ASN_INTEGER,
                                           entry->storageType);
                break;
            case COLUMN_NSVACMACCESSSTATUS:
                snmp_set_var_typed_integer(request->requestvb, ASN_INTEGER,
                                           entry->status);
                break;
            }
        }
        break;

#ifndef NETSNMP_NO_WRITE_SUPPORT
        /*
         * Write-support
         */
    case MODE_SET_RESERVE1:
        for (request = requests; request; request = request->next) {
            entry = (struct vacm_accessEntry *)
                netsnmp_extract_iterator_context(request);
            table_info = netsnmp_extract_table_info(request);
            ret = SNMP_ERR_NOERROR;

            switch (table_info->colnum) {
            case COLUMN_NSVACMCONTEXTMATCH:
                ret = netsnmp_check_vb_int_range(request->requestvb, 1, 2);
                break;
            case COLUMN_NSVACMVIEWNAME:
                ret = netsnmp_check_vb_type_and_max_size(request->requestvb,
                                                         ASN_OCTET_STR,
                                                         VACM_MAX_STRING);
                break;
            case COLUMN_VACMACCESSSTORAGETYPE:
                ret = netsnmp_check_vb_storagetype(request->requestvb,
                          (/*entry ? entry->storageType :*/ SNMP_STORAGE_NONE));
                break;
            case COLUMN_NSVACMACCESSSTATUS:
                /*
                 * The usual 'check_vb_rowstatus' call is too simplistic
                 *   to be used here.  Because we're implementing a table
                 *   within an existing table, it's quite possible for a
                 *   the vacmAccessTable entry to exist, even if this is
                 *   a "new" nsVacmAccessEntry.
                 *
                 * We can check that the value being assigned is suitable
                 *   for a RowStatus syntax object, but the transition
                 *   checks need to be done explicitly.
                 */
                ret = netsnmp_check_vb_rowstatus_value(request->requestvb);
                if ( ret != SNMP_ERR_NOERROR )
                    break;

                /*
                 * Extract the authType token from the list of indexes
                 */
                idx = table_info->indexes->next_variable->next_variable->next_variable->next_variable;
                memset(atype, 0, sizeof(atype));
                memcpy(atype, (char *)idx->val.string, idx->val_len);
                viewIdx = se_find_value_in_slist(VACM_VIEW_ENUM_NAME, atype);
                if ( viewIdx < 0 ) {
                    ret = SNMP_ERR_NOCREATION;
                    break;
                }
                switch ( *request->requestvb->val.integer ) {
                case RS_ACTIVE:
                case RS_NOTINSERVICE:
                    /* Check that this particular view is already set */
                    if ( !entry || !entry->views[viewIdx][0] )
                        ret = SNMP_ERR_INCONSISTENTVALUE;
                    break;
                case RS_CREATEANDWAIT:
                case RS_CREATEANDGO:
                    /* Check that this particular view is not yet set */
                    if ( entry && entry->views[viewIdx][0] )
                        ret = SNMP_ERR_INCONSISTENTVALUE;
                    break;
                }
                break;
            } /* switch(colnum) */
            if ( ret != SNMP_ERR_NOERROR ) {
                netsnmp_set_request_error(reqinfo, request, ret);
                return SNMP_ERR_NOERROR;
            }
        }
        break;

    case MODE_SET_RESERVE2:
        for (request = requests; request; request = request->next) {
            entry = (struct vacm_accessEntry *)
                netsnmp_extract_iterator_context(request);
            table_info = netsnmp_extract_table_info(request);

            switch (table_info->colnum) {
            case COLUMN_NSVACMACCESSSTATUS:
                switch (*request->requestvb->val.integer) {
                case RS_CREATEANDGO:
                case RS_CREATEANDWAIT:
                    if (!entry) {
                         idx = table_info->indexes; gName = (char*)idx->val.string;
                         idx = idx->next_variable;  cPrefix = (char*)idx->val.string;
                         idx = idx->next_variable;  model = *idx->val.integer;
                         idx = idx->next_variable;  level = *idx->val.integer;
                         entry = vacm_createAccessEntry( gName, cPrefix, model, level );
                         entry->storageType = ST_NONVOLATILE;
                         netsnmp_insert_iterator_context(request, (void*)entry);
                    }
                }
            }
        }
        break;

    case MODE_SET_FREE:
    case MODE_SET_UNDO:
        /* XXX - TODO */
        break;

    case MODE_SET_ACTION:
        /* ??? Empty ??? */
        break;

    case MODE_SET_COMMIT:
        for (request = requests; request; request = request->next) {
            entry = (struct vacm_accessEntry *)
                netsnmp_extract_iterator_context(request);
            table_info = netsnmp_extract_table_info(request);
            if ( !entry )
                continue;  /* Shouldn't happen */

            /* Extract the authType token from the list of indexes */
            idx = table_info->indexes->next_variable->next_variable->next_variable->next_variable;
            memset(atype, 0, sizeof(atype));
            memcpy(atype, (char *)idx->val.string, idx->val_len);
            viewIdx = se_find_value_in_slist(VACM_VIEW_ENUM_NAME, atype);
            if (viewIdx < 0)
                    continue;

            switch (table_info->colnum) {
            case COLUMN_NSVACMCONTEXTMATCH:
                entry->contextMatch = *request->requestvb->val.integer;
                break;
            case COLUMN_NSVACMVIEWNAME:
                memset( entry->views[viewIdx], 0, VACMSTRINGLEN );
                memcpy( entry->views[viewIdx], request->requestvb->val.string,
                                               request->requestvb->val_len);
                break;
            case COLUMN_VACMACCESSSTORAGETYPE:
                entry->storageType = *request->requestvb->val.integer;
                break;
            case COLUMN_NSVACMACCESSSTATUS:
                switch (*request->requestvb->val.integer) {
                case RS_DESTROY:
                    memset( entry->views[viewIdx], 0, VACMSTRINGLEN );
                    break;
                }
                break;
            }
        }
        break;
#endif /* !NETSNMP_NO_WRITE_SUPPORT */
    }
    return SNMP_ERR_NOERROR;
}
Exemple #21
0
int
icmp_handler(netsnmp_mib_handler          *handler,
             netsnmp_handler_registration *reginfo,
             netsnmp_agent_request_info   *reqinfo,
             netsnmp_request_info         *requests)
{
    netsnmp_request_info  *request;
    netsnmp_variable_list *requestvb;
    long     ret_value;
    oid      subid;
#ifdef USES_TRADITIONAL_ICMPSTAT
    int      i;
#endif

    /*
     * The cached data should already have been loaded by the
     *    cache handler, higher up the handler chain.
     * But just to be safe, check this and load it manually if necessary
     */
#ifndef hpux11
    if (!netsnmp_cache_is_valid(reqinfo, reginfo->handlerName)) {
        netsnmp_assert("cache" == "valid"); /* always false */
        icmp_load( NULL, NULL );	/* XXX - check for failure */
    }
#endif


    /*
     * 
     *
     */
    DEBUGMSGTL(("mibII/icmp", "Handler - mode %s\n",
                    se_find_label_in_slist("agent_mode", reqinfo->mode)));
    switch (reqinfo->mode) {
    case MODE_GET:
        for (request=requests; request; request=request->next) {
            requestvb = request->requestvb;
            subid = requestvb->name[OID_LENGTH(icmp_oid)];  /* XXX */
            DEBUGMSGTL(( "mibII/icmp", "oid: "));
            DEBUGMSGOID(("mibII/icmp", requestvb->name,
                                       requestvb->name_length));
            DEBUGMSG((   "mibII/icmp", "\n"));

            switch (subid) {
#ifdef USES_SNMP_DESIGNED_ICMPSTAT
    case ICMPINMSGS:
        ret_value = icmpstat.icmpInMsgs;
        break;
    case ICMPINERRORS:
        ret_value = icmpstat.icmpInErrors;
        break;
    case ICMPINDESTUNREACHS:
        ret_value = icmpstat.icmpInDestUnreachs;
        break;
    case ICMPINTIMEEXCDS:
        ret_value = icmpstat.icmpInTimeExcds;
        break;
    case ICMPINPARMPROBS:
        ret_value = icmpstat.icmpInParmProbs;
        break;
    case ICMPINSRCQUENCHS:
        ret_value = icmpstat.icmpInSrcQuenchs;
        break;
    case ICMPINREDIRECTS:
        ret_value = icmpstat.icmpInRedirects;
        break;
    case ICMPINECHOS:
        ret_value = icmpstat.icmpInEchos;
        break;
    case ICMPINECHOREPS:
        ret_value = icmpstat.icmpInEchoReps;
        break;
    case ICMPINTIMESTAMPS:
        ret_value = icmpstat.icmpInTimestamps;
        break;
    case ICMPINTIMESTAMPREPS:
        ret_value = icmpstat.icmpInTimestampReps;
        break;
    case ICMPINADDRMASKS:
        ret_value = icmpstat.icmpInAddrMasks;
        break;
    case ICMPINADDRMASKREPS:
        ret_value = icmpstat.icmpInAddrMaskReps;
        break;
    case ICMPOUTMSGS:
        ret_value = icmpstat.icmpOutMsgs;
        break;
    case ICMPOUTERRORS:
        ret_value = icmpstat.icmpOutErrors;
        break;
    case ICMPOUTDESTUNREACHS:
        ret_value = icmpstat.icmpOutDestUnreachs;
        break;
    case ICMPOUTTIMEEXCDS:
        ret_value = icmpstat.icmpOutTimeExcds;
        break;
    case ICMPOUTPARMPROBS:
        ret_value = icmpstat.icmpOutParmProbs;
        break;
    case ICMPOUTSRCQUENCHS:
        ret_value = icmpstat.icmpOutSrcQuenchs;
        break;
    case ICMPOUTREDIRECTS:
        ret_value = icmpstat.icmpOutRedirects;
        break;
    case ICMPOUTECHOS:
        ret_value = icmpstat.icmpOutEchos;
        break;
    case ICMPOUTECHOREPS:
        ret_value = icmpstat.icmpOutEchoReps;
        break;
    case ICMPOUTTIMESTAMPS:
        ret_value = icmpstat.icmpOutTimestamps;
        break;
    case ICMPOUTTIMESTAMPREPS:
        ret_value = icmpstat.icmpOutTimestampReps;
        break;
    case ICMPOUTADDRMASKS:
        ret_value = icmpstat.icmpOutAddrMasks;
        break;
    case ICMPOUTADDRMASKREPS:
        ret_value = icmpstat.icmpOutAddrMaskReps;
        break;
#else                          /* USES_SNMP_DESIGNED_ICMPSTAT */

#ifdef USES_TRADITIONAL_ICMPSTAT
    case ICMPINMSGS:
        ret_value = icmpstat.icps_badcode +
            icmpstat.icps_tooshort +
            icmpstat.icps_checksum + icmpstat.icps_badlen;
        for (i = 0; i <= ICMP_MAXTYPE; i++)
            ret_value += icmpstat.icps_inhist[i];
        break;
    case ICMPINERRORS:
        ret_value = icmpstat.icps_badcode +
            icmpstat.icps_tooshort +
            icmpstat.icps_checksum + icmpstat.icps_badlen;
        break;
    case ICMPINDESTUNREACHS:
        ret_value = icmpstat.icps_inhist[ICMP_UNREACH];
        break;
    case ICMPINTIMEEXCDS:
        ret_value = icmpstat.icps_inhist[ICMP_TIMXCEED];
        break;
    case ICMPINPARMPROBS:
        ret_value = icmpstat.icps_inhist[ICMP_PARAMPROB];
        break;
    case ICMPINSRCQUENCHS:
        ret_value = icmpstat.icps_inhist[ICMP_SOURCEQUENCH];
        break;
    case ICMPINREDIRECTS:
        ret_value = icmpstat.icps_inhist[ICMP_REDIRECT];
        break;
    case ICMPINECHOS:
        ret_value = icmpstat.icps_inhist[ICMP_ECHO];
        break;
    case ICMPINECHOREPS:
        ret_value = icmpstat.icps_inhist[ICMP_ECHOREPLY];
        break;
    case ICMPINTIMESTAMPS:
        ret_value = icmpstat.icps_inhist[ICMP_TSTAMP];
        break;
    case ICMPINTIMESTAMPREPS:
        ret_value = icmpstat.icps_inhist[ICMP_TSTAMPREPLY];
        break;
    case ICMPINADDRMASKS:
        ret_value = icmpstat.icps_inhist[ICMP_MASKREQ];
        break;
    case ICMPINADDRMASKREPS:
        ret_value = icmpstat.icps_inhist[ICMP_MASKREPLY];
        break;
    case ICMPOUTMSGS:
        ret_value = icmpstat.icps_oldshort + icmpstat.icps_oldicmp;
        for (i = 0; i <= ICMP_MAXTYPE; i++)
            ret_value += icmpstat.icps_outhist[i];
        break;
    case ICMPOUTERRORS:
        ret_value = icmpstat.icps_oldshort + icmpstat.icps_oldicmp;
        break;
    case ICMPOUTDESTUNREACHS:
        ret_value = icmpstat.icps_outhist[ICMP_UNREACH];
        break;
    case ICMPOUTTIMEEXCDS:
        ret_value = icmpstat.icps_outhist[ICMP_TIMXCEED];
        break;
    case ICMPOUTPARMPROBS:
        ret_value = icmpstat.icps_outhist[ICMP_PARAMPROB];
        break;
    case ICMPOUTSRCQUENCHS:
        ret_value = icmpstat.icps_outhist[ICMP_SOURCEQUENCH];
        break;
    case ICMPOUTREDIRECTS:
        ret_value = icmpstat.icps_outhist[ICMP_REDIRECT];
        break;
    case ICMPOUTECHOS:
        ret_value = icmpstat.icps_outhist[ICMP_ECHO];
        break;
    case ICMPOUTECHOREPS:
        ret_value = icmpstat.icps_outhist[ICMP_ECHOREPLY];
        break;
    case ICMPOUTTIMESTAMPS:
        ret_value = icmpstat.icps_outhist[ICMP_TSTAMP];
        break;
    case ICMPOUTTIMESTAMPREPS:
        ret_value = icmpstat.icps_outhist[ICMP_TSTAMPREPLY];
        break;
    case ICMPOUTADDRMASKS:
        ret_value = icmpstat.icps_outhist[ICMP_MASKREQ];
        break;
    case ICMPOUTADDRMASKREPS:
        ret_value = icmpstat.icps_outhist[ICMP_MASKREPLY];
        break;
#else                          /* USES_TRADITIONAL_ICMPSTAT */

#ifdef hpux11
    case ICMPINMSGS:
    case ICMPINERRORS:
    case ICMPINDESTUNREACHS:
    case ICMPINTIMEEXCDS:
    case ICMPINPARMPROBS:
    case ICMPINSRCQUENCHS:
    case ICMPINREDIRECTS:
    case ICMPINECHOS:
    case ICMPINECHOREPS:
    case ICMPINTIMESTAMPS:
    case ICMPINTIMESTAMPREPS:
    case ICMPINADDRMASKS:
    case ICMPINADDRMASKREPS:
    case ICMPOUTMSGS:
    case ICMPOUTERRORS:
    case ICMPOUTDESTUNREACHS:
    case ICMPOUTTIMEEXCDS:
    case ICMPOUTPARMPROBS:
    case ICMPOUTSRCQUENCHS:
    case ICMPOUTREDIRECTS:
    case ICMPOUTECHOS:
    case ICMPOUTECHOREPS:
    case ICMPOUTTIMESTAMPS:
    case ICMPOUTTIMESTAMPREPS:
    case ICMPOUTADDRMASKS:
    case ICMPOUTADDRMASKREPS:
	/*
	 * This is a bit of a hack, to shoehorn the HP-UX 11
	 * single-object retrieval approach into the caching
	 * architecture.
	 */
	if (icmp_load(NULL, (void*)subid) == -1 ) {
            netsnmp_set_request_error(reqinfo, request, SNMP_NOSUCHOBJECT);
            continue;
	}
        ret_value = icmpstat;
        break;
#else                          /* hpux11 */

#ifdef WIN32
    case ICMPINMSGS:
        ret_value = icmpstat.stats.icmpInStats.dwMsgs;
        break;
    case ICMPINERRORS:
        ret_value = icmpstat.stats.icmpInStats.dwErrors;
        break;
    case ICMPINDESTUNREACHS:
        ret_value = icmpstat.stats.icmpInStats.dwDestUnreachs;
        break;
    case ICMPINTIMEEXCDS:
        ret_value = icmpstat.stats.icmpInStats.dwTimeExcds;
        break;
    case ICMPINPARMPROBS:
        ret_value = icmpstat.stats.icmpInStats.dwParmProbs;
        break;
    case ICMPINSRCQUENCHS:
        ret_value = icmpstat.stats.icmpInStats.dwSrcQuenchs;
        break;
    case ICMPINREDIRECTS:
        ret_value = icmpstat.stats.icmpInStats.dwRedirects;
        break;
    case ICMPINECHOS:
        ret_value = icmpstat.stats.icmpInStats.dwEchos;
        break;
    case ICMPINECHOREPS:
        ret_value = icmpstat.stats.icmpInStats.dwEchoReps;
        break;
    case ICMPINTIMESTAMPS:
        ret_value = icmpstat.stats.icmpInStats.dwTimestamps;
        break;
    case ICMPINTIMESTAMPREPS:
        ret_value = icmpstat.stats.icmpInStats.dwTimestampReps;
        break;
    case ICMPINADDRMASKS:
        ret_value = icmpstat.stats.icmpInStats.dwAddrMasks;
        break;
    case ICMPINADDRMASKREPS:
        ret_value = icmpstat.stats.icmpInStats.dwAddrMaskReps;
        break;
    case ICMPOUTMSGS:
        ret_value = icmpstat.stats.icmpOutStats.dwMsgs;
        break;
    case ICMPOUTERRORS:
        ret_value = icmpstat.stats.icmpOutStats.dwErrors;
        break;
    case ICMPOUTDESTUNREACHS:
        ret_value = icmpstat.stats.icmpOutStats.dwDestUnreachs;
        break;
    case ICMPOUTTIMEEXCDS:
        ret_value = icmpstat.stats.icmpOutStats.dwTimeExcds;
        break;
    case ICMPOUTPARMPROBS:
        ret_value = icmpstat.stats.icmpOutStats.dwParmProbs;
        break;
    case ICMPOUTSRCQUENCHS:
        ret_value = icmpstat.stats.icmpOutStats.dwSrcQuenchs;
        break;
    case ICMPOUTREDIRECTS:
        ret_value = icmpstat.stats.icmpOutStats.dwRedirects;
        break;
    case ICMPOUTECHOS:
        ret_value = icmpstat.stats.icmpOutStats.dwEchos;
        break;
    case ICMPOUTECHOREPS:
        ret_value = icmpstat.stats.icmpOutStats.dwEchoReps;
        break;
    case ICMPOUTTIMESTAMPS:
        ret_value = icmpstat.stats.icmpOutStats.dwTimestamps;
        break;
    case ICMPOUTTIMESTAMPREPS:
        ret_value = icmpstat.stats.icmpOutStats.dwTimestampReps;
        break;
    case ICMPOUTADDRMASKS:
        ret_value = icmpstat.stats.icmpOutStats.dwAddrMasks;
        break;
    case ICMPOUTADDRMASKREPS:
        ret_value = icmpstat.stats.icmpOutStats.dwAddrMaskReps;
        break;
#endif                          /* WIN32 */
#endif                          /* hpux11 */
#endif                          /* USES_TRADITIONAL_ICMPSTAT */
#endif                          /* USES_SNMP_DESIGNED_ICMPSTAT */
	    }
	    snmp_set_var_typed_value(request->requestvb, ASN_COUNTER,
			             (u_char *)&ret_value, sizeof(ret_value));
	}
        break;

    case MODE_GETNEXT:
    case MODE_GETBULK:
    case MODE_SET_RESERVE1:
    case MODE_SET_RESERVE2:
    case MODE_SET_ACTION:
    case MODE_SET_COMMIT:
    case MODE_SET_FREE:
    case MODE_SET_UNDO:
        snmp_log(LOG_WARNING, "mibII/icmp: Unsupported mode (%d)\n",
                               reqinfo->mode);
        break;
    default:
        snmp_log(LOG_WARNING, "mibII/icmp: Unrecognised mode (%d)\n",
                               reqinfo->mode);
        break;
    }

    return SNMP_ERR_NOERROR;
}
void
return_delayed_response(unsigned int clientreg, void *clientarg)
{
    /*
     * extract the cache from the passed argument 
     */
    netsnmp_delegated_cache *cache = (netsnmp_delegated_cache *) clientarg;

    netsnmp_request_info *requests;
    netsnmp_agent_request_info *reqinfo;
    u_long         *delay_time_cache = NULL;

    /*
     * here we double check that the cache we created earlier is still
     * * valid.  If not, the request timed out for some reason and we
     * * don't need to keep processing things.  Should never happen, but
     * * this double checks. 
     */
    cache = netsnmp_handler_check_cache(cache);

    if (!cache) {
        snmp_log(LOG_ERR, "illegal call to return delayed response\n");
        return;
    }

    /*
     * re-establish the previous pointers we are used to having 
     */
    reqinfo = cache->reqinfo;
    requests = cache->requests;

    DEBUGMSGTL(("delayed_instance",
                "continuing delayed request, mode = %d\n",
                cache->reqinfo->mode));

    /*
     * mention that it's no longer delegated, and we've now answered
     * the query (which we'll do down below). 
     */
    requests->delegated = 0;

    switch (cache->reqinfo->mode) {
        /*
         * registering as an instance means we don't need to deal with
         * getnext processing, so we don't handle it here at all.
         * 
         * However, since the instance handler already reset the mode
         * back to GETNEXT from the faked GET mode, we need to do the
         * same thing in both cases.  This should be fixed in future
         * versions of net-snmp hopefully. 
         */

    case MODE_GET:
    case MODE_GETNEXT:
        /*
         * return the currend delay time 
         */
        snmp_set_var_typed_value(cache->requests->requestvb,
                                 ASN_INTEGER,
                                 (u_char *) & delay_time,
                                 sizeof(delay_time));
        break;

#ifndef NETSNMP_NO_WRITE_SUPPORT
    case MODE_SET_RESERVE1:
        /*
         * check type 
         */
        if (requests->requestvb->type != ASN_INTEGER) {
            /*
             * not an integer.  Bad dog, no bone. 
             */
            netsnmp_set_request_error(reqinfo, requests,
                                      SNMP_ERR_WRONGTYPE);
            /*
             * we don't need the cache any longer 
             */
            netsnmp_free_delegated_cache(cache);
            return;
        }
        break;

    case MODE_SET_RESERVE2:
        /*
         * store old value for UNDO support in the future. 
         */
        delay_time_cache = netsnmp_memdup(&delay_time, sizeof(delay_time));

        /*
         * malloc failed 
         */
        if (delay_time_cache == NULL) {
            netsnmp_set_request_error(reqinfo, requests,
                                      SNMP_ERR_RESOURCEUNAVAILABLE);
            netsnmp_free_delegated_cache(cache);
            return;
        }

        /*
         * Add our temporary information to the request itself.
         * This is then retrivable later.  The free function
         * passed auto-frees it when the request is later
         * deleted.  
         */
        netsnmp_request_add_list_data(requests,
                                      netsnmp_create_data_list
                                      (DELAYED_INSTANCE_SET_NAME,
                                       delay_time_cache, free));
        break;

    case MODE_SET_ACTION:
        /*
         * update current value 
         */
        delay_time = *(requests->requestvb->val.integer);
        DEBUGMSGTL(("testhandler", "updated delay_time -> %ld\n",
                    delay_time));
        break;

    case MODE_SET_UNDO:
        /*
         * ack, something somewhere failed.  We reset back to the
         * previously old value by extracting the previosuly
         * stored information back out of the request 
         */
        delay_time =
            *((u_long *) netsnmp_request_get_list_data(requests,
                                                       DELAYED_INSTANCE_SET_NAME));
        break;

    case MODE_SET_COMMIT:
    case MODE_SET_FREE:
        /*
         * the only thing to do here is free the old memdup'ed
         * value, but it's auto-freed by the datalist recovery, so
         * we don't have anything to actually do here 
         */
        break;
#endif /* NETSNMP_NO_WRITE_SUPPORT */
    }

    /*
     * free the information cache 
     */
    netsnmp_free_delegated_cache(cache);
}
/** handles requests for the expObjectTable table */
int
expObjectTable_handler(netsnmp_mib_handler *handler,
                       netsnmp_handler_registration *reginfo,
                       netsnmp_agent_request_info *reqinfo,
                       netsnmp_request_info *requests)
{

    netsnmp_request_info       *request;
    netsnmp_table_request_info *tinfo;
    netsnmp_tdata_row          *row;
    struct expObject           *entry;
    struct expExpression       *exp;
    char   expOwner[EXP_STR1_LEN+1];
    char   expName[ EXP_STR1_LEN+1];
    long   objIndex;
    long   ret;
    netsnmp_variable_list *vp;

    DEBUGMSGTL(("disman:expr:mib", "Expression Object Table handler (%d)\n",
                                    reqinfo->mode));
    switch (reqinfo->mode) {
        /*
         * Read-support (also covers GetNext requests)
         */
    case MODE_GET:
        for (request = requests; request; request = request->next) {
            entry = (struct expObject *)netsnmp_tdata_extract_entry(request);
            tinfo = netsnmp_extract_table_info(request);
            if (!entry || !(entry->flags & EXP_OBJ_FLAG_VALID))
                continue;

            switch (tinfo->colnum) {
            case COLUMN_EXPOBJECTID:
                snmp_set_var_typed_value(request->requestvb, ASN_OBJECT_ID,
                              (u_char *) entry->expObjectID,
                                         entry->expObjectID_len*sizeof(oid));
                break;
            case COLUMN_EXPOBJECTIDWILDCARD:
                ret = (entry->flags & EXP_OBJ_FLAG_OWILD) ?
                           TV_TRUE : TV_FALSE;
                snmp_set_var_typed_integer(request->requestvb, ASN_INTEGER, ret);
                break;
            case COLUMN_EXPOBJECTSAMPLETYPE:
                snmp_set_var_typed_integer(request->requestvb, ASN_INTEGER,
                                           entry->expObjectSampleType);
                break;
            case COLUMN_EXPOBJECTDELTADISCONTINUITYID:
                /*
                 * "This object [and the next two] are instantiated only if
                 *  expObjectSampleType is 'deltaValue' or 'changedValue'"
                 */
                if ( entry->expObjectSampleType == 1 )
                    continue;
                snmp_set_var_typed_value(request->requestvb, ASN_OBJECT_ID,
                              (u_char *) entry->expObjDeltaD,
                                         entry->expObjDeltaD_len*sizeof(oid));
                break;
            case COLUMN_EXPOBJECTDISCONTINUITYIDWILDCARD:
                if ( entry->expObjectSampleType == 1 )
                    continue;
                ret = (entry->flags & EXP_OBJ_FLAG_DWILD) ?
                           TV_TRUE : TV_FALSE;
                snmp_set_var_typed_integer(request->requestvb, ASN_INTEGER, ret);
                break;
            case COLUMN_EXPOBJECTDISCONTINUITYIDTYPE:
                if ( entry->expObjectSampleType == 1 )
                    continue;
                snmp_set_var_typed_integer(request->requestvb, ASN_INTEGER,
                                           entry->expObjDiscontinuityType);
                break;
            case COLUMN_EXPOBJECTCONDITIONAL:
                snmp_set_var_typed_value(request->requestvb, ASN_OBJECT_ID,
                              (u_char *) entry->expObjCond,
                                         entry->expObjCond_len*sizeof(oid));
                break;
            case COLUMN_EXPOBJECTCONDITIONALWILDCARD:
		ret = (entry->flags & EXP_OBJ_FLAG_CWILD) ?
                           TV_TRUE : TV_FALSE;
                snmp_set_var_typed_integer(request->requestvb, ASN_INTEGER, ret);
                break;
            case COLUMN_EXPOBJECTENTRYSTATUS:
                /* What would indicate 'notReady' ? */
                ret = (entry->flags & EXP_OBJ_FLAG_ACTIVE) ?
                          RS_ACTIVE : RS_NOTINSERVICE;
                snmp_set_var_typed_integer(request->requestvb, ASN_INTEGER, ret);
                break;
            }
        }
        break;

        /*
         * Write-support
         */
    case MODE_SET_RESERVE1:
        for (request = requests; request; request = request->next) {
            entry = (struct expObject *)
                netsnmp_tdata_extract_entry(request);
            tinfo = netsnmp_extract_table_info(request);

            switch (tinfo->colnum) {
            case COLUMN_EXPOBJECTID:
            case COLUMN_EXPOBJECTDELTADISCONTINUITYID:
            case COLUMN_EXPOBJECTCONDITIONAL:
                ret = netsnmp_check_vb_oid(request->requestvb);
                if (ret != SNMP_ERR_NOERROR) {
                    netsnmp_set_request_error(reqinfo, request, ret);
                    return SNMP_ERR_NOERROR;
                }
                break;

            case COLUMN_EXPOBJECTIDWILDCARD:
            case COLUMN_EXPOBJECTDISCONTINUITYIDWILDCARD:
            case COLUMN_EXPOBJECTCONDITIONALWILDCARD:
                ret = netsnmp_check_vb_truthvalue(request->requestvb);
                if (ret != SNMP_ERR_NOERROR) {
                    netsnmp_set_request_error(reqinfo, request, ret);
                    return SNMP_ERR_NOERROR;
                }
                break;

            case COLUMN_EXPOBJECTSAMPLETYPE:
            case COLUMN_EXPOBJECTDISCONTINUITYIDTYPE:
                ret = netsnmp_check_vb_int_range(request->requestvb, 1, 3);
                if (ret != SNMP_ERR_NOERROR) {
                    netsnmp_set_request_error(reqinfo, request, ret);
                    return SNMP_ERR_NOERROR;
                }
                break;

            case COLUMN_EXPOBJECTENTRYSTATUS:
                ret = netsnmp_check_vb_rowstatus(request->requestvb,
                          (entry ? RS_ACTIVE : RS_NONEXISTENT));
                if (ret != SNMP_ERR_NOERROR) {
                    netsnmp_set_request_error(reqinfo, request, ret);
                    return SNMP_ERR_NOERROR;
                }
                break;
            default:
                netsnmp_set_request_error(reqinfo, request,
                                          SNMP_ERR_NOTWRITABLE);
                return SNMP_ERR_NOERROR;
            }
        }
        break;

    case MODE_SET_RESERVE2:
        for (request = requests; request; request = request->next) {
            tinfo = netsnmp_extract_table_info(request);

            switch (tinfo->colnum) {
            case COLUMN_EXPOBJECTENTRYSTATUS:
                switch (*request->requestvb->val.integer) {
                case RS_CREATEANDGO:
                case RS_CREATEANDWAIT:
                    /*
                     * Create an (empty) new row structure
                     */
                    memset(expOwner, 0, sizeof(expOwner));
                    memcpy(expOwner, tinfo->indexes->val.string,
                                     tinfo->indexes->val_len);
                    memset(expName,  0, sizeof(expName));
                    memcpy(expName,
                           tinfo->indexes->next_variable->val.string,
                           tinfo->indexes->next_variable->val_len);
                    vp = tinfo->indexes->next_variable->next_variable;
                    objIndex = *vp->val.integer;

                    row = expObject_createRow(expOwner, expName, objIndex, 0);
                    if (!row) {
                        netsnmp_set_request_error(reqinfo, request,
                                                  SNMP_ERR_RESOURCEUNAVAILABLE);
                        return SNMP_ERR_NOERROR;
                    }
                    netsnmp_insert_tdata_row( request, row );
                }
            }
        }
        break;

    case MODE_SET_FREE:
        for (request = requests; request; request = request->next) {
            tinfo = netsnmp_extract_table_info(request);

            switch (tinfo->colnum) {
            case COLUMN_EXPOBJECTENTRYSTATUS:
                switch (*request->requestvb->val.integer) {
                case RS_CREATEANDGO:
                case RS_CREATEANDWAIT:
                    /*
                     * Tidy up after a failed row creation request
                     */ 
                    entry = (struct expObject *)
                                netsnmp_tdata_extract_entry(request);
                    if (entry &&
                      !(entry->flags & EXP_OBJ_FLAG_VALID)) {
                        row = (netsnmp_tdata_row *)
                                netsnmp_tdata_extract_row(request);
                        expObject_removeEntry( row );
                    }
                }
            }
        }
        break;

    case MODE_SET_ACTION:
        for (request = requests; request; request = request->next) {
            tinfo = netsnmp_extract_table_info(request);
            entry = (struct expObject *)
                    netsnmp_tdata_extract_entry(request);
            if (!entry) {
                /*
                 * New rows must be created via the RowStatus column
                 */
                netsnmp_set_request_error(reqinfo, request,
                                          SNMP_ERR_NOCREATION);
                                      /* or inconsistentName? */
                return SNMP_ERR_NOERROR;

            }
        }
        break;

    case MODE_SET_UNDO:
        break;

    case MODE_SET_COMMIT:
        /*
         * All these assignments are "unfailable", so it's
         *  (reasonably) safe to apply them in the Commit phase
         */
        ret = 0;  /* Flag to re-check expExpressionPrefix settings */
        for (request = requests; request; request = request->next) {
            entry = (struct expObject *) netsnmp_tdata_extract_entry(request);
            tinfo = netsnmp_extract_table_info(request);

            switch (tinfo->colnum) {
            case COLUMN_EXPOBJECTID:
                memset(entry->expObjectID, 0, sizeof(entry->expObjectID));
                memcpy(entry->expObjectID, request->requestvb->val.string,
                                           request->requestvb->val_len);
                entry->expObjectID_len = request->requestvb->val_len;
                break;
            case COLUMN_EXPOBJECTIDWILDCARD:
                if (*request->requestvb->val.integer == TV_TRUE)
                    entry->flags |=  EXP_OBJ_FLAG_OWILD;
                else
                    entry->flags &= ~EXP_OBJ_FLAG_OWILD;
                break;
            case COLUMN_EXPOBJECTSAMPLETYPE:
                entry->expObjectSampleType = *request->requestvb->val.integer;
                break;
            case COLUMN_EXPOBJECTDELTADISCONTINUITYID:
                memset(entry->expObjDeltaD, 0, sizeof(entry->expObjDeltaD));
                memcpy(entry->expObjDeltaD, request->requestvb->val.string,
                                            request->requestvb->val_len);
                entry->expObjDeltaD_len = request->requestvb->val_len/sizeof(oid);
               /* XXX
                if ( snmp_oid_compare( entry->expObjDeltaD,
                                       entry->expObjDeltaD_len, 
                                       sysUpTime_inst,
                                       sysUpTime_inst_len ) != 0 )
                    entry->flags |= EXP_OBJ_FLAG_DDISC;
               */

                /*
                 * If the OID used for the expExpressionPrefix object
                 *   has changed, then update the expression structure.
                 */
                if ( entry->flags & EXP_OBJ_FLAG_PREFIX ) {
                    exp = expExpression_getEntry( entry->expOwner,
                                                  entry->expName );
                    memcpy( exp->expPrefix, entry->expObjDeltaD,
                            MAX_OID_LEN*sizeof(oid));
                    exp->expPrefix_len = entry->expObjDeltaD_len;
                }
                break;
            case COLUMN_EXPOBJECTDISCONTINUITYIDWILDCARD:
                if (*request->requestvb->val.integer == TV_TRUE) {
                    /*
                     * Possible new prefix OID candidate
                     * Can't set the value here, since the OID
                     *    assignment might not have been processed yet.
                     */
                    exp = expExpression_getEntry( entry->expOwner,
                                                  entry->expName );
                    if (exp && exp->expPrefix_len == 0 )
                        ret = 1;   /* Set the prefix later  */
                    entry->flags |=  EXP_OBJ_FLAG_DWILD;
                } else {
                    if ( entry->flags | EXP_OBJ_FLAG_PREFIX ) {
                        exp = expExpression_getEntry( entry->expOwner,
                                                      entry->expName );
                        memset( exp->expPrefix, 0, MAX_OID_LEN*sizeof(oid));
                        exp->expPrefix_len = 0;
                        ret = 1;   /* Need a new prefix OID */
                    }
                    entry->flags &= ~EXP_OBJ_FLAG_DWILD;
                }
                break;
            case COLUMN_EXPOBJECTDISCONTINUITYIDTYPE:
                entry->expObjDiscontinuityType =
                           *request->requestvb->val.integer;
                break;
            case COLUMN_EXPOBJECTCONDITIONAL:
                memset(entry->expObjCond, 0, sizeof(entry->expObjCond));
                memcpy(entry->expObjCond, request->requestvb->val.string,
                                          request->requestvb->val_len);
                entry->expObjCond_len = request->requestvb->val_len/sizeof(oid);
                break;
            case COLUMN_EXPOBJECTCONDITIONALWILDCARD:
                if (*request->requestvb->val.integer == TV_TRUE)
                    entry->flags |=  EXP_OBJ_FLAG_CWILD;
                else
                    entry->flags &= ~EXP_OBJ_FLAG_CWILD;
                break;
            case COLUMN_EXPOBJECTENTRYSTATUS:
                switch (*request->requestvb->val.integer) {
                case RS_ACTIVE:
                    entry->flags |= EXP_OBJ_FLAG_ACTIVE;
                    break;
                case RS_NOTINSERVICE:
                    entry->flags &= ~EXP_OBJ_FLAG_ACTIVE;
                    break;
                case RS_CREATEANDGO:
                    entry->flags |= EXP_OBJ_FLAG_ACTIVE;
                    entry->flags |= EXP_OBJ_FLAG_VALID;
                    break;
                case RS_CREATEANDWAIT:
                    entry->flags |= EXP_OBJ_FLAG_VALID;
                    break;

                case RS_DESTROY:
                    row = (netsnmp_tdata_row *)
                               netsnmp_tdata_extract_row(request);
                    expObject_removeEntry(row);
                }
            }
        }

        /*
         * Need to check for changes in expExpressionPrefix handling
         */
        for (request = requests; request; request = request->next) {
            entry = (struct expObject *) netsnmp_tdata_extract_entry(request);
            tinfo = netsnmp_extract_table_info(request);

            switch (tinfo->colnum) {
            case COLUMN_EXPOBJECTDISCONTINUITYIDWILDCARD:
                /*
                 * If a column has just been marked as wild,
                 *   then consider using it as the prefix OID
                 */
                if (*request->requestvb->val.integer == TV_TRUE) {
                    exp = expExpression_getEntry( entry->expOwner,
                                                  entry->expName );
                    if ( exp->expPrefix_len == 0 ) {
                        memcpy( exp->expPrefix, entry->expObjDeltaD,
                                MAX_OID_LEN*sizeof(oid));
                        exp->expPrefix_len = entry->expObjDeltaD_len;
                        entry->flags |= EXP_OBJ_FLAG_PREFIX;
                    }
                }
                /*
                 * If it's just been marked as non-wildcarded
                 *   then we need to look for a new candidate.
                 */
                else {

                }
                break;
            }
        }
        break;
    }
    DEBUGMSGTL(("disman:expr:mib", "Expression Object handler - done \n"));
    return SNMP_ERR_NOERROR;
}
/** handles requests for the tlstmCertToTSNTable table */
static int
tlstmCertToTSNTable_handler(netsnmp_mib_handler *handler,
                            netsnmp_handler_registration *reginfo,
                            netsnmp_agent_request_info *reqinfo,
                            netsnmp_request_info *requests)
{
    oid tsnm[] = { SNMP_TLS_TM_BASE, 1, 1, 0 };
    static const int tsnm_pos = OID_LENGTH(tsnm) - 1;
    netsnmp_request_info *request = NULL;
    netsnmp_table_request_info *info;
    netsnmp_tdata  *table;
    netsnmp_tdata_row *row;
    certToTSN_entry *entry;
    int             ret = SNMP_ERR_NOERROR;

    DEBUGMSGTL(("tlstmCertToSN:handler", "Processing request (mode %s (%d))\n",
                se_find_label_in_slist("agent_mode", reqinfo->mode),
                reqinfo->mode));

    switch (reqinfo->mode) {
    /** ######################################################### GET #####
     *
     *   Read-support (also covers GetNext requests)
     */
    case MODE_GET:
        for (request = requests; request; request = request->next) {
            if (request->processed)
                continue;

            entry = (certToTSN_entry *) netsnmp_tdata_extract_entry(request);
            info = netsnmp_extract_table_info(request);
            netsnmp_assert(entry && info);

            switch (info->colnum) {
            case COL_SNMPTLSTMCERTTOTSN_FINGERPRINT:
            {
                /*
                 * build SnmpTLSFingerprint
                 */
                u_char bin[42], *ptr = bin;
                size_t len = sizeof(bin);
                int    rc;
                rc = netsnmp_tls_fingerprint_build(entry->hashType,
                                                   entry->fingerprint,
                                                   &ptr, &len, 0);
                if (SNMPERR_SUCCESS != rc)
                    netsnmp_set_request_error(reqinfo, request,
                                              SNMP_ERR_GENERR);
                else
                    snmp_set_var_typed_value(request->requestvb, ASN_OCTET_STR,
                                             bin, len);
            }
                break;          /* case COL_SNMPTLSTMCERTTOTSN_FINGERPRINT */
            case COL_SNMPTLSTMCERTTOTSN_MAPTYPE:
                tsnm[tsnm_pos] = entry->mapType;
                snmp_set_var_typed_value(request->requestvb, ASN_OBJECT_ID,
                                         tsnm, sizeof(tsnm));
                break;          /* case COL_SNMPTLSTMCERTTOTSN_MAPTYPE */
            case COL_SNMPTLSTMCERTTOTSN_DATA:
                snmp_set_var_typed_value(request->requestvb, ASN_OCTET_STR,
                                         entry->data, entry->data_len);
                break;          /* case COL_SNMPTLSTMCERTTOTSN_DATA */
            case COL_SNMPTLSTMCERTTOTSN_STORAGETYPE:
                snmp_set_var_typed_integer(request->requestvb, ASN_INTEGER,
                                           entry->storageType);
                break;          /* case COL_SNMPTLSTMCERTTOTSN_STORAGETYPE */
            case COL_SNMPTLSTMCERTTOTSN_ROWSTATUS:
                snmp_set_var_typed_integer(request->requestvb, ASN_INTEGER,
                                           entry->rowStatus);
                break;          /* case COL_SNMPTLSTMCERTTOTSN_ROWSTATUS */
            default:
                netsnmp_set_request_error(reqinfo, request, SNMP_NOSUCHOBJECT);
                break;
            }                   /* switch colnum */
        }                       /* for requests */
        break;                  /* case MODE_GET */

        /*
         * Write-support
         */
    /** #################################################### RESERVE1 #####
     *
     *   In RESERVE1 we are just checking basic ASN.1 size/type restrictions.
     * You probably don't need to change any of this code. Don't change any
     * of the column values here. Save that for the ACTION phase.
     *
     *   The next phase is RESERVE2 or FREE.
     */
    case MODE_SET_RESERVE1:
        for (request = requests; request; request = request->next) {
            netsnmp_assert(request->processed == 0);

            entry = (certToTSN_entry *) netsnmp_tdata_extract_entry(request);
            info = netsnmp_extract_table_info(request);

            if ((NULL != entry) && (ST_READONLY == entry->storageType)) {
                ret = SNMP_ERR_NOTWRITABLE;
                break;
            }

            switch (info->colnum) {
            case COL_SNMPTLSTMCERTTOTSN_FINGERPRINT:
                ret = netsnmp_check_vb_type_and_max_size
                    (request->requestvb, ASN_OCTET_STR,
                     sizeof(entry->fingerprint));
                /** check len/algorithm MIB requirements */
                if (ret == SNMP_ERR_NOERROR)
                    ret = netsnmp_cert_check_vb_fingerprint(request->requestvb);
                break;          /* case COL_SNMPTLSTMCERTTOTSN_FINGERPRINT */
            case COL_SNMPTLSTMCERTTOTSN_MAPTYPE:
                ret = netsnmp_check_vb_type_and_max_size
                    (request->requestvb, ASN_OBJECT_ID,
                     SNMPTLSTMCERTTOTSN_MAPTYPE_MAX_SIZE);
                if (ret == SNMP_ERR_NOERROR) {
                    if (_oid2type(request->requestvb->val.objid,
                                  request->requestvb->val_len) >
                        TSNM_tlstmCert_MAX)
                        ret = SNMP_ERR_WRONGVALUE;
                }
                break;          /* case COL_SNMPTLSTMCERTTOTSN_MAPTYPE */
            case COL_SNMPTLSTMCERTTOTSN_DATA:
                ret = netsnmp_check_vb_type_and_max_size
                    (request->requestvb, ASN_OCTET_STR, sizeof(entry->data));
                break;          /* case COL_SNMPTLSTMCERTTOTSN_DATA */
            case COL_SNMPTLSTMCERTTOTSN_STORAGETYPE:
                ret = netsnmp_check_vb_storagetype
                    (request->requestvb,(entry ? entry->storageType : ST_NONE));
                break;          /* case COL_SNMPTLSTMCERTTOTSN_STORAGETYPE */
            case COL_SNMPTLSTMCERTTOTSN_ROWSTATUS:
                ret = netsnmp_check_vb_rowstatus_with_storagetype
                    (request->requestvb,
                     (entry ? entry->rowStatus :RS_NONEXISTENT),
                     (entry ? entry->storageType :ST_NONE));
                break;          /* case COL_SNMPTLSTMCERTTOTSN_ROWSTATUS */
            default:
                ret = SNMP_ERR_NOTWRITABLE;
            }                   /* switch colnum */

            if (ret != SNMP_ERR_NOERROR)
                break;
        }                       /* for requests */
        break;                  /* case MODE_SET_RESERVE1 */

    /** #################################################### RESERVE2 #####
     *
     *   RESERVE2 is for checking additional restrictions from the MIB.
     * Since these restrictions are often in the description of the object,
     * mib2c can't generate code. It's possible that you need to add
     * additional checks here. However, don't change any of the column
     * values here. Save that for the ACTION phase.
     *
     *   The next phase is ACTION or FREE.
     */
    case MODE_SET_RESERVE2:
        for (request = requests; request; request = request->next) {
            netsnmp_assert(request->processed == 0);

            entry = (certToTSN_entry *) netsnmp_tdata_extract_entry(request);
            table = netsnmp_tdata_extract_table(request);
            info = netsnmp_extract_table_info(request);
            /*
             * if no row, create one
             */
            if (!entry) {
                row = tlstmCertToTSNTable_createEntry
                    (table,*info->indexes->val.integer);
                if (!row) {
                    ret = SNMP_ERR_RESOURCEUNAVAILABLE;
                    break;
                }
                entry = row->data;
                _allocUndo(entry);
                if (!entry->undo) {
                    tlstmCertToTSNTable_removeEntry(table, row);
                    row = NULL;
                    ret = SNMP_ERR_RESOURCEUNAVAILABLE;
                    break;
                }
                entry->undo->fate = FATE_NEWLY_CREATED;
                /** associate row with requests */
                netsnmp_insert_tdata_row(request, row);
            }

            /** allocate undo structure, if needed */
            if (!entry->undo) {
                _allocUndo(entry);
                if (!entry->undo) {
                    ret = SNMP_ERR_RESOURCEUNAVAILABLE;
                    break;
                }
            }

            /*
             * save request ptr for column. if we already
             * have a value, bail.
             */
            if (entry->undo->req[info->colnum]) {
                DEBUGMSGT(("tlstmCertToSN:reserve2",
                           "multiple sets to col %d in request\n",
                           info->colnum));
                if (FATE_NEWLY_CREATED == entry->undo->fate)
                    ret = SNMP_ERR_INCONSISTENTNAME;
                else
                    ret = SNMP_ERR_INCONSISTENTVALUE;
                break;
            }
            entry->undo->req[info->colnum] = request;
            if (ret != SNMP_ERR_NOERROR)
                break;
        }                       /* for requests */

        if (ret == SNMP_ERR_NOERROR) {
            /** make sure rowstatus is used to create rows */
            for (request = requests; request; request = request->next) {
                if (request->processed)
                    continue;

                entry = (certToTSN_entry *)
                    netsnmp_tdata_extract_entry(request);
                if ((entry->undo->fate != FATE_NEWLY_CREATED) ||
                    (entry->undo->req[COL_SNMPTLSTMCERTTOTSN_ROWSTATUS]))
                    continue;
                ret = SNMP_ERR_INCONSISTENTNAME;
                break;
            } /* creation for requests */
        } /* no error */
        break;                  /* case MODE_SET_RESERVE2 */

    /** ######################################################## FREE #####
     *
     *   FREE is for cleaning up after a failed request (during either
     * RESERVE1 or RESERVE2). So any allocated resources need to be
     * released.
     *
     *   This the final phase for this path in the state machine.
     */
    case MODE_SET_FREE:
        /*
         * release undo resources
         * remove any newly created rows
         */
        for (request = requests; request; request = request->next) {
            table = netsnmp_tdata_extract_table(request);
            row = netsnmp_tdata_extract_row(request);
            entry = (certToTSN_entry *) netsnmp_tdata_extract_entry(request);

            if (!entry || !entry->undo)
                continue;

            /** disassociate row with requests */
            netsnmp_remove_tdata_row(request, row);

            if (FATE_NEWLY_CREATED == entry->undo->fate)
                tlstmCertToTSNTable_removeEntry(table, row);
            else
                _freeUndo(entry);
        }
        break;                  /* case MODE_SET_FREE */

    /** ###################################################### ACTION #####
     *
     *   In the ACTION phase, we perform any sets that can be undone.
     * (Save anything that can't be undone for the COMMIT phase.)
     *
     *   After individual columns have been done, you should check that the
     * row as a whole is consistent.
     *
     * The next phase is UNDO or COMMIT.
     */
    case MODE_SET_ACTION:
        for (request = requests; request; request = request->next) {
            entry = (certToTSN_entry *) netsnmp_tdata_extract_entry(request);
            info = netsnmp_extract_table_info(request);

            /** reserve2 should enforce this */
            netsnmp_assert(request == entry->undo->req[info->colnum]);

            /*
             * for each col, save old value and the set new value
             */
            switch (info->colnum) {
            case COL_SNMPTLSTMCERTTOTSN_FINGERPRINT:
            {
                u_char *tmp = (u_char*)entry->fingerprint;
                u_int size = sizeof(entry->fingerprint);
                netsnmp_variable_list *vb = request->requestvb;

                memcpy(entry->undo->fingerprint,
                       entry->fingerprint, sizeof(entry->fingerprint));
                entry->undo->fingerprint_len = entry->fingerprint_len;
                entry->undo->hashType = entry->hashType;
                memset(entry->fingerprint, 0, sizeof(entry->fingerprint));

                (void)netsnmp_tls_fingerprint_parse(vb->val.string, vb->val_len,
                                                    (char**)&tmp, &size, 0,
                                                    &entry->hashType);
                entry->fingerprint_len = size;
                if (0 == entry->fingerprint_len)
                    ret = SNMP_ERR_GENERR;
            }
                break;          /* case COL_SNMPTLSTMCERTTOTSN_FINGERPRINT */
            case COL_SNMPTLSTMCERTTOTSN_MAPTYPE:
                entry->undo->mapType = entry->mapType;
                entry->mapType = _oid2type(request->requestvb->val.objid,
                                           request->requestvb->val_len);
                break;          /* case COL_SNMPTLSTMCERTTOTSN_MAPTYPE */
            case COL_SNMPTLSTMCERTTOTSN_DATA:
                memcpy(entry->undo->data, entry->data, sizeof(entry->data));
                entry->undo->data_len = entry->data_len;
                memset(entry->data, 0, sizeof(entry->data));
                memcpy(entry->data, request->requestvb->val.string,
                       request->requestvb->val_len);
                entry->data_len = request->requestvb->val_len;
                break;          /* case COL_SNMPTLSTMCERTTOTSN_DATA */
            case COL_SNMPTLSTMCERTTOTSN_STORAGETYPE:
                entry->undo->storageType = entry->storageType;
                entry->storageType = *request->requestvb->val.integer;
                break;          /* case COL_SNMPTLSTMCERTTOTSN_STORAGETYPE */
            case COL_SNMPTLSTMCERTTOTSN_ROWSTATUS:
                entry->undo->rowStatus = entry->rowStatus;
                entry->rowStatus = *request->requestvb->val.integer;
                break;          /* case COL_SNMPTLSTMCERTTOTSN_ROWSTATUS */
            }                   /* switch colnum */
        }                       /* set values for requests */

        if (ret != SNMP_ERR_NOERROR) 
            break; /* skip consistency if we've already got error */

        /*
         * All columns now have their final values set. check the
         * internal consistency of each row.
         */
        for (request = requests; request; request = request->next) {
            entry = (certToTSN_entry *) netsnmp_tdata_extract_entry(request);
            info = netsnmp_extract_table_info(request);

            if (entry->undo->is_consistent != -1)
                continue;       /* already checked */

            /** assume consistency */
            entry->undo->is_consistent = 1;

            /*
             * per mib, can't have empty fingerprint and must
             * have data if indicated by map type.
             */
            if (0 == entry->fingerprint_len) {
                DEBUGMSGTL(("tlstmCertToTSNTable:inconsistent",
                            "fingerprint must not be empty\n"));
                entry->undo->is_consistent = 0;
            }
            else if ((TSNM_tlstmCertSpecified == entry->mapType) &&
                     (0 == entry->data_len)) {
                DEBUGMSGTL(("tlstmCertToTSNTable:inconsistent",
                            "must specify Data for CertSpecified identity\n"));
                entry->undo->is_consistent = 0;
            }

            if ((RS_IS_ACTIVE(entry->rowStatus)) &&
                ((!entry->undo->req[COL_SNMPTLSTMCERTTOTSN_ROWSTATUS]) ||
                 (RS_IS_ACTIVE(entry->undo->rowStatus)))) {
                /*
                 * per mib, can't modify these while row active
                 */
                char _cols[3] = { COL_SNMPTLSTMCERTTOTSN_FINGERPRINT,
                                  COL_SNMPTLSTMCERTTOTSN_MAPTYPE, COL_SNMPTLSTMCERTTOTSN_DATA };
                int i;
                for (i=0; i < 3; ++i ) {
                    if (!entry->undo->req[i])
                        continue;
                    DEBUGMSGTL(("tlstmCertToTSNTable:inconsistent",
                                "can't modify row %d while active\n",
                                _cols[i]));
                    entry->undo->is_consistent = 0;
                    ret = SNMP_ERR_NOTWRITABLE;
                    request= entry->undo->req[i];
                    break;
                }
            } else if (RS_IS_GOING_ACTIVE(entry->rowStatus)) {
                /*
                 * if going active, inconsistency is fatal
                 */
                if (!entry->undo->is_consistent) {
                    netsnmp_assert(entry->undo->req[COL_SNMPTLSTMCERTTOTSN_ROWSTATUS]);
                    if (FATE_NEWLY_CREATED == entry->undo->fate)
                        ret = SNMP_ERR_INCONSISTENTNAME;
                    else
                        ret = SNMP_ERR_INCONSISTENTVALUE;
                    request = entry->undo->req[COL_SNMPTLSTMCERTTOTSN_ROWSTATUS];
                }
            } else if (RS_DESTROY == entry->rowStatus) {
                /*
                 * can't destroy active row
                 */
                if (RS_IS_ACTIVE(entry->undo->rowStatus)) {
                    DEBUGMSGTL(("tlstmCertToTSNTable:inconsistent",
                                "can't destroy active row\n"));
                    netsnmp_assert(entry->undo->req[COL_SNMPTLSTMCERTTOTSN_ROWSTATUS]);
                    ret = SNMP_ERR_INCONSISTENTVALUE;
                    request = entry->undo->req[COL_SNMPTLSTMCERTTOTSN_ROWSTATUS];
                }
            }
            if (ret != SNMP_ERR_NOERROR)
                break;
        }                       /* consistency for requests */
        break;                  /* case MODE_SET_ACTION */

    /** ######################################################## UNDO #####
     *
     *   UNDO is for cleaning up any failed requests that went through the
     * ACTION phase.
     *
     *   This the final phase for this path in the state machine.
     */
    case MODE_SET_UNDO:
        for (request = requests; request; request = request->next) {
            row = netsnmp_tdata_extract_row(request);
            entry = (certToTSN_entry *) netsnmp_tdata_extract_entry(request);
            info = netsnmp_extract_table_info(request);

            /*
             * skip newly created rows, as we're going to delete
             * them below anyways
             */
            if (FATE_NEWLY_CREATED == entry->undo->fate)
                continue;

            /*
             * restore values
             */
            switch (info->colnum) {
            case COL_SNMPTLSTMCERTTOTSN_FINGERPRINT:
                memcpy(entry->fingerprint, entry->undo->fingerprint,
                       sizeof(entry->fingerprint));
                entry->fingerprint_len = entry->undo->fingerprint_len;
                entry->hashType = entry->undo->hashType;
                break;          /* case COL_SNMPTLSTMCERTTOTSN_FINGERPRINT */
            case COL_SNMPTLSTMCERTTOTSN_MAPTYPE:
                entry->mapType = entry->undo->mapType;
                break;          /* case COL_SNMPTLSTMCERTTOTSN_MAPTYPE */
            case COL_SNMPTLSTMCERTTOTSN_DATA:
                memcpy(entry->data, entry->undo->data, sizeof(entry->data));
                entry->data_len = entry->undo->data_len;
                break;          /* case COL_SNMPTLSTMCERTTOTSN_DATA */
            case COL_SNMPTLSTMCERTTOTSN_STORAGETYPE:
                entry->storageType = entry->undo->storageType;
                break;          /* case COL_SNMPTLSTMCERTTOTSN_STORAGETYPE */
            case COL_SNMPTLSTMCERTTOTSN_ROWSTATUS:
                entry->rowStatus = entry->undo->rowStatus;
                break;          /* case COL_SNMPTLSTMCERTTOTSN_ROWSTATUS */
            }                   /* switch colnum */
        }                       /* for requests */

        /*
         * release undo data
         * or remove any newly created rows
         */
        for (request = requests; request; request = request->next) {
            table = netsnmp_tdata_extract_table(request);
            row = netsnmp_tdata_extract_row(request);
            entry = (certToTSN_entry *) netsnmp_tdata_extract_entry(request);

            if (!entry || !entry->undo)
                continue;

            /** disassociate row with requests */
            netsnmp_remove_tdata_row(request, row);

            if (FATE_NEWLY_CREATED == entry->undo->fate)
                tlstmCertToTSNTable_removeEntry(table, row);
            else
                _freeUndo(entry);
        }                       /* for requests */
        break;                  /* case MODE_SET_UNDO */

    /** ###################################################### COMMIT #####
     *
     *   COMMIT is the final success state, when all changes are finalized.
     * There is not recovery state should something faile here.
     *
     *   This the final phase for this path in the state machine.
     */
    case MODE_SET_COMMIT:
        for (request = requests; request; request = request->next) {
            row = netsnmp_tdata_extract_row(request);
            table = netsnmp_tdata_extract_table(request);
            info = netsnmp_extract_table_info(request);
            entry = (certToTSN_entry *) netsnmp_tdata_extract_entry(request);

            if ((RS_NOTREADY == entry->rowStatus) && entry->undo->is_consistent)
                entry->rowStatus = RS_NOTINSERVICE;
            else if ((RS_NOTINSERVICE == entry->rowStatus) &&
                     (0 == entry->undo->is_consistent))
                entry->rowStatus = RS_NOTREADY;

            /** release undo data for requests with no rowstatus */
            if (entry->undo && !entry->undo->req[COL_SNMPTLSTMCERTTOTSN_ROWSTATUS]) {
                _freeUndo(entry);
                if ((0 == entry->map_flags) && (entry->rowStatus == RS_ACTIVE))
                    _cert_map_add(entry);
                else if ((0 != entry->map_flags) &&
                         (entry->rowStatus == RS_DESTROY))
                    _cert_map_remove(entry);
            }

            switch (info->colnum) {
            case COL_SNMPTLSTMCERTTOTSN_ROWSTATUS:
                switch (entry->rowStatus) {
                case RS_CREATEANDGO:
                    /** Fall-through */
                case RS_ACTIVE:
                    netsnmp_assert(entry->undo->is_consistent);
                    entry->rowStatus = RS_ACTIVE;
                    if (0 == entry->map_flags)
                        _cert_map_add(entry);
                    break;

                case RS_CREATEANDWAIT:
                    /** Fall-through */
                case RS_NOTINSERVICE:
                    /** simply set status based on consistency */
                    if (entry->undo->is_consistent)
                        entry->rowStatus = RS_NOTINSERVICE;
                    else
                        entry->rowStatus = RS_NOTREADY;
                    if (0 != entry->map_flags)
                        _cert_map_remove(entry);
                    break;

                case RS_DESTROY:
                    /** remove from cert map */
                    if (0 != entry->map_flags)
                        _cert_map_remove(entry);
                    /** disassociate row with requests */
                    netsnmp_remove_tdata_row(request, row);
                    tlstmCertToTSNTable_removeEntry(table, row);
                    row = NULL;
                    entry = NULL;
                }
                /** release undo data */
                _freeUndo(entry);
                break;          /* case COL_SNMPTLSTMCERTTOTSN_ROWSTATUS */

            case COL_SNMPTLSTMCERTTOTSN_STORAGETYPE:
                if (RS_ACTIVE == entry->rowStatus)
                    _cert_map_tweak_storage(entry);
                break;          /* case COL_SNMPTLSTMCERTTOTSN_STORAGETYPE */

            case COL_SNMPTLSTMCERTTOTSN_FINGERPRINT:
            case COL_SNMPTLSTMCERTTOTSN_MAPTYPE:
            case COL_SNMPTLSTMCERTTOTSN_DATA:
                break;
            }                   /* switch colnum */

        }                       /* for requests */

        /** update last changed */
        _last_changed = netsnmp_get_agent_uptime();

        /** set up to save persistent store */
        snmp_store_needed(NULL);

        break;                  /* case MODE_SET_COMMIT */
    }                           /* switch (reqinfo->mode) */

    if (ret != SNMP_ERR_NOERROR)
        netsnmp_set_request_error(reqinfo, request, ret);

    return SNMP_ERR_NOERROR;
}
Exemple #25
0
void
group_requests (netsnmp_agent_request_info * agtreq_info,
                netsnmp_request_info * requests, netsnmp_container * request_group, table_container_data * tad)
{
    netsnmp_table_request_info *tblreq_info;

    netsnmp_index *row, *tmp, index;

    netsnmp_request_info *current;

    netsnmp_request_group *g;

    netsnmp_request_group_item *i;

    for (current = requests; current; current = current->next)
    {
        /*
         * skip anything that doesn't need processing.
         */
        if (current->processed != 0)
        {
            DEBUGMSGTL (("table_array:group", "already processed\n"));
            continue;
        }

        /*
         * 3.2.1 Setup and paranoia
         * *
         * * Get pointer to the table information for this request. This
         * * information was saved by table_helper_handler. When
         * * debugging, we double check a few assumptions. For example,
         * * the table_helper_handler should enforce column boundaries.
         */
        row = NULL;
        tblreq_info = netsnmp_extract_table_info (current);
        netsnmp_assert (tblreq_info->colnum <= tad->tblreg_info->max_column);

        /*
         * search for index
         */
        index.oids = tblreq_info->index_oid;
        index.len = tblreq_info->index_oid_len;
        tmp = (netsnmp_index *) CONTAINER_FIND (request_group, &index);
        if (tmp)
        {
            DEBUGMSGTL (("table_array:group", "    existing group:"));
            DEBUGMSGOID (("table_array:group", index.oids, index.len));
            DEBUGMSG (("table_array:group", "\n"));
            g = (netsnmp_request_group *) tmp;
            i = SNMP_MALLOC_TYPEDEF (netsnmp_request_group_item);
            if (i == NULL)
                return;
            i->ri = current;
            i->tri = tblreq_info;
            i->next = g->list;
            g->list = i;

            /** xxx-rks: store map of colnum to request */
            continue;
        }

        DEBUGMSGTL (("table_array:group", "    new group"));
        DEBUGMSGOID (("table_array:group", index.oids, index.len));
        DEBUGMSG (("table_array:group", "\n"));
        g = SNMP_MALLOC_TYPEDEF (netsnmp_request_group);
        i = SNMP_MALLOC_TYPEDEF (netsnmp_request_group_item);
        if (i == NULL || g == NULL)
        {
            SNMP_FREE (i);
            SNMP_FREE (g);
            return;
        }
        g->list = i;
        g->table = tad->table;
        i->ri = current;
        i->tri = tblreq_info;

        /** xxx-rks: store map of colnum to request */

        /*
         * search for row. all changes are made to the original row,
         * later, we'll make a copy in undo_info before we start processing.
         */
        row = g->existing_row = (netsnmp_index *) CONTAINER_FIND (tad->table, &index);
        if (!g->existing_row)
        {
            if (!tad->cb->create_row)
            {
#ifndef NETSNMP_NO_WRITE_SUPPORT
                if (MODE_IS_SET (agtreq_info->mode))
                    netsnmp_set_request_error (agtreq_info, current, SNMP_ERR_NOTWRITABLE);
                else
#endif                            /* NETSNMP_NO_WRITE_SUPPORT */
                    netsnmp_set_request_error (agtreq_info, current, SNMP_NOSUCHINSTANCE);
                free (g);
                free (i);
                continue;
            }

            /** use undo_info temporarily */
            row = g->existing_row = tad->cb->create_row (&index);
            if (!row)
            {
                /* xxx-rks : parameter to create_row to allow
                 * for better error reporting. */
                netsnmp_set_request_error (agtreq_info, current, SNMP_ERR_GENERR);
                free (g);
                free (i);
                continue;
            }
            g->row_created = 1;
        }

        g->index.oids = row->oids;
        g->index.len = row->len;

        CONTAINER_INSERT (request_group, g);

    } /** for( current ... ) */
}
int
handle_AcCfServerPasswd(netsnmp_mib_handler *handler,
                          netsnmp_handler_registration *reginfo,
                          netsnmp_agent_request_info   *reqinfo,
                          netsnmp_request_info         *requests)
{
    /* We are never called for a GETNEXT if it's registered as a
       "instance", as it's "magically" handled for us.  */

    /* a instance handler also only hands us one request at a time, so
       we don't need to loop over a list of requests; we'll only get one. */

	snmp_log(LOG_DEBUG, "enter handle_AcCfServerPasswd\n");

    switch(reqinfo->mode) {

        case MODE_GET:
            snmp_set_var_typed_value(requests->requestvb, ASN_OCTET_STR,
                                     (u_char *)acFileLoadInfo.passWord /* XXX: a pointer to the scalar's data */,
                                     strlen(acFileLoadInfo.passWord));
            break;

        /*
         * SET REQUEST
         *
         * multiple states in the transaction.  See:
         * http://www.net-snmp.org/tutorial-5/toolkit/mib_module/set-actions.jpg
         */
        case MODE_SET_RESERVE1:
			#if 0
            if (/* XXX: check incoming data in requests->requestvb->val.XXX for failures, like an incorrect type or an illegal value or ... */) {
                netsnmp_set_request_error(reqinfo, requests, /* XXX: set error code depending on problem (like SNMP_ERR_WRONGTYPE or SNMP_ERR_WRONGVALUE or ... */);
            }
			#endif
            break;

        case MODE_SET_RESERVE2:
			#if 0
            /* XXX malloc "undo" storage buffer */
            if (/* XXX if malloc, or whatever, failed: */) {
                netsnmp_set_request_error(reqinfo, requests, SNMP_ERR_RESOURCEUNAVAILABLE);
            }
			#endif
            break;

        case MODE_SET_FREE:
            /* XXX: free resources allocated in RESERVE1 and/or
               RESERVE2.  Something failed somewhere, and the states
               below won't be called. */
            break;

        case MODE_SET_ACTION:
			{
				if(TRANSFERRING == get_trans_status(CONF_TRANS_STATUS))
				{
					netsnmp_set_request_error(reqinfo, requests, SNMP_ERR_WRONGTYPE/* some error */);
					break;
				}				
				if (requests->requestvb->val_len < 1 /* XXX: error? */) {
					netsnmp_set_request_error(reqinfo, requests, SNMP_ERR_WRONGTYPE/* some error */);
				}
				else
				{
					memset( acFileLoadInfo.passWord, 0, sizeof(acFileLoadInfo.passWord) );
					strncpy( acFileLoadInfo.passWord, requests->requestvb->val.string, sizeof(acFileLoadInfo.passWord) );
					check_and_do_load();
					snmp_log(LOG_ERR, "acFileLoadInfo.passWord\n", acFileLoadInfo.passWord );
				}
			}

            break;

        case MODE_SET_COMMIT:
			#if 0
            /* XXX: delete temporary storage */
            if (/* XXX: error? */) {
                /* try _really_really_ hard to never get to this point */
                netsnmp_set_request_error(reqinfo, requests, SNMP_ERR_COMMITFAILED);
            }
			#endif
            break;

        case MODE_SET_UNDO:
			#if 0
            /* XXX: UNDO and return to previous value for the object */
            if (/* XXX: error? */) {
                /* try _really_really_ hard to never get to this point */
                netsnmp_set_request_error(reqinfo, requests, SNMP_ERR_UNDOFAILED);
            }
			#endif
            break;

        default:
            /* we should never get here, so this is a really bad error */
            snmp_log(LOG_ERR, "unknown mode (%d) in handle_AcCfServerPasswd\n", reqinfo->mode );
            return SNMP_ERR_GENERR;
    }

	snmp_log(LOG_DEBUG, "exit handle_AcCfServerPasswd\n");
    return SNMP_ERR_NOERROR;
}
Exemple #27
0
int
ip_handler(netsnmp_mib_handler          *handler,
           netsnmp_handler_registration *reginfo,
           netsnmp_agent_request_info   *reqinfo,
           netsnmp_request_info         *requests)
{
    netsnmp_request_info  *request;
    netsnmp_variable_list *requestvb;
    long     ret_value;
    oid      subid;
    int      type = ASN_COUNTER;

    /*
     * The cached data should already have been loaded by the
     *    cache handler, higher up the handler chain.
     */
#ifdef _USE_PERFSTAT_PROTOCOL
    ip_load(NULL, NULL);
#endif


    /*
     * 
     *
     */
    DEBUGMSGTL(("mibII/ip", "Handler - mode %s\n",
                    se_find_label_in_slist("agent_mode", reqinfo->mode)));
    switch (reqinfo->mode) {
    case MODE_GET:
        for (request=requests; request; request=request->next) {
            requestvb = request->requestvb;
            subid = requestvb->name[OID_LENGTH(ip_oid)];  /* XXX */
            DEBUGMSGTL(( "mibII/ip", "oid: "));
            DEBUGMSGOID(("mibII/ip", requestvb->name,
                                     requestvb->name_length));
            DEBUGMSG((   "mibII/ip", "\n"));

            switch (subid) {
#ifdef USES_SNMP_DESIGNED_IPSTAT
    case IPFORWARDING:
        ret_value = ipstat.ipForwarding;
        type = ASN_INTEGER;
        break;
    case IPDEFAULTTTL:
        ret_value = ipstat.ipDefaultTTL;
        type = ASN_INTEGER;
        break;
    case IPINRECEIVES:
        ret_value = ipstat.ipInReceives & 0xffffffff;
        break;
    case IPINHDRERRORS:
        ret_value = ipstat.ipInHdrErrors;
        break;
    case IPINADDRERRORS:
        ret_value = ipstat.ipInAddrErrors;
        break;
    case IPFORWDATAGRAMS:
        ret_value = ipstat.ipForwDatagrams;
        break;
    case IPINUNKNOWNPROTOS:
        ret_value = ipstat.ipInUnknownProtos;
        break;
    case IPINDISCARDS:
        ret_value = ipstat.ipInDiscards;
        break;
    case IPINDELIVERS:
        ret_value = ipstat.ipInDelivers & 0xffffffff;
        break;
    case IPOUTREQUESTS:
        ret_value = ipstat.ipOutRequests & 0xffffffff;
        break;
    case IPOUTDISCARDS:
        ret_value = ipstat.ipOutDiscards;
        break;
    case IPOUTNOROUTES:
        ret_value = ipstat.ipOutNoRoutes;
        break;
    case IPREASMTIMEOUT:
        ret_value = ipstat.ipReasmTimeout;
        type = ASN_INTEGER;
        break;
    case IPREASMREQDS:
        ret_value = ipstat.ipReasmReqds;
        break;
    case IPREASMOKS:
        ret_value = ipstat.ipReasmOKs;
        break;
    case IPREASMFAILS:
        ret_value = ipstat.ipReasmFails;
        break;
    case IPFRAGOKS:
        ret_value = ipstat.ipFragOKs;
        break;
    case IPFRAGFAILS:
        ret_value = ipstat.ipFragFails;
        break;
    case IPFRAGCREATES:
        ret_value = ipstat.ipFragCreates;
        break;
    case IPROUTEDISCARDS:
        ret_value = ipstat.ipRoutingDiscards;
        break;

#elif defined(USES_TRADITIONAL_IPSTAT) && !defined(_USE_PERFSTAT_PROTOCOL)
#ifdef HAVE_SYS_TCPIPSTATS_H
    /*
     * This actually reads statistics for *all* the groups together,
     * so we need to isolate the IP-specific bits.  
     */
#define	ipstat		ipstat.ipstat
#endif
    case IPFORWARDING:
    case IPDEFAULTTTL:
        /* 
         * Query these two individually
         */
        ret_value = ip_load(NULL, (void *)subid);
        if (ret_value == -1 ) {
            netsnmp_set_request_error(reqinfo, request, SNMP_NOSUCHOBJECT);
            continue;
	}
        type = ASN_INTEGER;
        break;
    case IPINRECEIVES:
        ret_value = ipstat.ips_total & 0xffffffff;
        break;
    case IPINHDRERRORS:
        ret_value = ipstat.ips_badsum
            + ipstat.ips_tooshort
            + ipstat.ips_toosmall + ipstat.ips_badhlen + ipstat.ips_badlen;
        break;
    case IPINADDRERRORS:
        ret_value = ipstat.ips_cantforward;
        break;
    case IPFORWDATAGRAMS:
        ret_value = ipstat.ips_forward;
        break;
    case IPINUNKNOWNPROTOS:
#if HAVE_STRUCT_IPSTAT_IPS_NOPROTO
        ret_value = ipstat.ips_noproto;
        break;
#else
        netsnmp_set_request_error(reqinfo, request, SNMP_NOSUCHOBJECT);
        continue;
#endif
    case IPINDISCARDS:
#if HAVE_STRUCT_IPSTAT_IPS_FRAGDROPPED
        ret_value = ipstat.ips_fragdropped;   /* ?? */
        break;
#else
        netsnmp_set_request_error(reqinfo, request, SNMP_NOSUCHOBJECT);
        continue;
#endif
    case IPINDELIVERS:
#if HAVE_STRUCT_IPSTAT_IPS_DELIVERED
        ret_value = ipstat.ips_delivered & 0xffffffff;
        break;
#else
        netsnmp_set_request_error(reqinfo, request, SNMP_NOSUCHOBJECT);
        continue;
#endif
    case IPOUTREQUESTS:
#if HAVE_STRUCT_IPSTAT_IPS_LOCALOUT
        ret_value = ipstat.ips_localout & 0xffffffff;
        break;
#else
        netsnmp_set_request_error(reqinfo, request, SNMP_NOSUCHOBJECT);
        continue;
#endif
    case IPOUTDISCARDS:
#if HAVE_STRUCT_IPSTAT_IPS_ODROPPED
        ret_value = ipstat.ips_odropped;
        break;
#else
        netsnmp_set_request_error(reqinfo, request, SNMP_NOSUCHOBJECT);
        continue;
#endif
    case IPOUTNOROUTES:
        /*
         * XXX: how to calculate this (counts dropped routes, not packets)?
         * ipstat.ips_cantforward isn't right, as it counts packets.
         * ipstat.ips_noroute is also incorrect.
         */
        netsnmp_set_request_error(reqinfo, request, SNMP_NOSUCHOBJECT);
        continue;
    case IPREASMTIMEOUT:
        ret_value = IPFRAGTTL;
        type = ASN_INTEGER;
        break;
    case IPREASMREQDS:
        ret_value = ipstat.ips_fragments;
        break;
    case IPREASMOKS:
#if HAVE_STRUCT_IPSTAT_IPS_REASSEMBLED
        ret_value = ipstat.ips_reassembled;
        break;
#else
        netsnmp_set_request_error(reqinfo, request, SNMP_NOSUCHOBJECT);
        continue;
#endif
    case IPREASMFAILS:
        ret_value = ipstat.ips_fragdropped + ipstat.ips_fragtimeout;
        break;
    case IPFRAGOKS:
#if HAVE_STRUCT_IPSTAT_IPS_FRAGMENTED
        ret_value = ipstat.ips_fragments;
        break;
#else            /* XXX */
        ret_value = ipstat.ips_fragments
            - (ipstat.ips_fragdropped + ipstat.ips_fragtimeout);
        break;
#endif
    case IPFRAGFAILS:
#if HAVE_STRUCT_IPSTAT_IPS_CANTFRAG
        ret_value = ipstat.ips_cantfrag;
        break;
#else
        netsnmp_set_request_error(reqinfo, request, SNMP_NOSUCHOBJECT);
        continue;
#endif
    case IPFRAGCREATES:
#if HAVE_STRUCT_IPSTAT_IPS_OFRAGMENTS
        ret_value = ipstat.ips_ofragments;
        break;
#else
        netsnmp_set_request_error(reqinfo, request, SNMP_NOSUCHOBJECT);
        continue;
#endif
    case IPROUTEDISCARDS:
#if HAVE_STRUCT_IPSTAT_IPS_NOROUTE
        ret_value = ipstat.ips_noroute;
        break;
#else
        netsnmp_set_request_error(reqinfo, request, SNMP_NOSUCHOBJECT);
        continue;
#endif
#ifdef HAVE_SYS_TCPIPSTATS_H
#undef ipstat
#endif
#elif defined(hpux11)
    case IPFORWARDING:
    case IPDEFAULTTTL:
    case IPREASMTIMEOUT:
        type = ASN_INTEGER;
    case IPINRECEIVES:
    case IPINHDRERRORS:
    case IPINADDRERRORS:
    case IPFORWDATAGRAMS:
    case IPINUNKNOWNPROTOS:
    case IPINDISCARDS:
    case IPINDELIVERS:
    case IPOUTREQUESTS:
    case IPOUTDISCARDS:
    case IPOUTNOROUTES:
    case IPREASMREQDS:
    case IPREASMOKS:
    case IPREASMFAILS:
    case IPFRAGOKS:
    case IPFRAGFAILS:
    case IPFRAGCREATES:
    case IPROUTEDISCARDS:
	/*
	 * This is a bit of a hack, to shoehorn the HP-UX 11
	 * single-object retrieval approach into the caching
	 * architecture.
	 */
	if (ip_load(NULL, (void*)subid) == -1 ) {
            netsnmp_set_request_error(reqinfo, request, SNMP_NOSUCHOBJECT);
            continue;
	}
        ret_value = ipstat;
        break;
#elif defined (WIN32) || defined (cygwin)
    case IPFORWARDING:
        ipForwarding = ipstat.dwForwarding;
        ret_value    = ipstat.dwForwarding;
        type = ASN_INTEGER;
        break;
    case IPDEFAULTTTL:
        ipTTL     = ipstat.dwDefaultTTL;
        ret_value = ipstat.dwDefaultTTL;
        type = ASN_INTEGER;
        break;
    case IPINRECEIVES:
        ret_value = ipstat.dwInReceives;
        break;
    case IPINHDRERRORS:
        ret_value = ipstat.dwInHdrErrors;
        break;
    case IPINADDRERRORS:
        ret_value = ipstat.dwInAddrErrors;
        break;
    case IPFORWDATAGRAMS:
        ret_value = ipstat.dwForwDatagrams;
        break;
    case IPINUNKNOWNPROTOS:
        ret_value = ipstat.dwInUnknownProtos;
        break;
    case IPINDISCARDS:
        ret_value = ipstat.dwInDiscards;
        break;
    case IPINDELIVERS:
        ret_value = ipstat.dwInDelivers;
        break;
    case IPOUTREQUESTS:
        ret_value = ipstat.dwOutRequests;
        break;
    case IPOUTDISCARDS:
        ret_value = ipstat.dwOutDiscards;
        break;
    case IPOUTNOROUTES:
        ret_value = ipstat.dwOutNoRoutes;
        break;
    case IPREASMTIMEOUT:
        ret_value = ipstat.dwReasmTimeout;
        type = ASN_INTEGER;
        break;
    case IPREASMREQDS:
        ret_value = ipstat.dwReasmReqds;
        break;
    case IPREASMOKS:
        ret_value = ipstat.dwReasmOks;
        break;
    case IPREASMFAILS:
        ret_value = ipstat.dwReasmFails;
        break;
    case IPFRAGOKS:
        ret_value = ipstat.dwFragOks;
        break;
    case IPFRAGFAILS:
        ret_value = ipstat.dwFragFails;
        break;
    case IPFRAGCREATES:
        ret_value = ipstat.dwFragCreates;
        break;
    case IPROUTEDISCARDS:
        ret_value = ipstat.dwRoutingDiscards;
        break;
#elif defined(_USE_PERFSTAT_PROTOCOL)
    case IPFORWARDING:
        ret_value    = 0;
        type = ASN_INTEGER;
        break;
    case IPDEFAULTTTL:
        ret_value = 0;
        type = ASN_INTEGER;
        break;
    case IPINRECEIVES:
        ret_value = ps_proto.u.ip.ipackets;
        break;
    case IPINHDRERRORS:
    case IPINADDRERRORS:
    case IPFORWDATAGRAMS:
        ret_value = 0;
        break;
    case IPINUNKNOWNPROTOS:
        ret_value = ps_proto.u.ip.ierrors;
        break;
    case IPINDISCARDS:
        ret_value = 0;
        break;
    case IPINDELIVERS:
    case IPOUTREQUESTS:
        ret_value = ps_proto.u.ip.opackets;
        break;
    case IPOUTDISCARDS:
    case IPOUTNOROUTES:
        ret_value = 0;
        break;
    case IPREASMTIMEOUT:
        ret_value = 0;
        type = ASN_INTEGER;
        break;
    case IPREASMREQDS:
    case IPREASMOKS:
    case IPREASMFAILS:
    case IPFRAGOKS:
    case IPFRAGFAILS:
    case IPFRAGCREATES:
        ret_value = 0;
        break;
    case IPROUTEDISCARDS:
        ret_value = ps_proto.u.ip.oerrors;
        break;
#endif			/* USES_SNMP_DESIGNED_IPSTAT */

    case IPADDRTABLE:
    case IPROUTETABLE:
    case IPMEDIATABLE:
        /*
	 * These are not actually valid scalar objects.
	 * The relevant table registrations should take precedence,
	 *   so skip these three subtrees, regardless of architecture.
	 */
        netsnmp_set_request_error(reqinfo, request, SNMP_NOSUCHOBJECT);
        continue;

	    }
	    snmp_set_var_typed_value(request->requestvb, (u_char)type,
			             (u_char *)&ret_value, sizeof(ret_value));
	}
        break;

    case MODE_GETNEXT:
    case MODE_GETBULK:
#ifndef NETSNMP_NO_WRITE_SUPPORT
    case MODE_SET_RESERVE1:
		/* XXX - Windows currently supports setting this */
    case MODE_SET_RESERVE2:
    case MODE_SET_ACTION:
    case MODE_SET_COMMIT:
    case MODE_SET_FREE:
    case MODE_SET_UNDO:
        snmp_log(LOG_WARNING, "mibII/ip: Unsupported mode (%d)\n",
                               reqinfo->mode);
        break;
#endif /* !NETSNMP_NO_WRITE_SUPPORT */
    default:
        snmp_log(LOG_WARNING, "mibII/ip: Unrecognised mode (%d)\n",
                               reqinfo->mode);
        break;
    }

    return SNMP_ERR_NOERROR;
}
Exemple #28
0
/** handles requests for the ipCidrRouteTable table, if anything else
   needs to be done */
int
ipCidrRouteTable_handler(netsnmp_mib_handler *handler,
                         netsnmp_handler_registration *reginfo,
                         netsnmp_agent_request_info *reqinfo,
                         netsnmp_request_info *requests)
{

    netsnmp_request_info *request;
    netsnmp_table_request_info *table_info;
    netsnmp_variable_list *var;

    void           *data_context;

    oid            *suffix;
    size_t          suffix_len;

    /** column and row index encoded portion */
    suffix = requests->requestvb->name + reginfo->rootoid_len + 1;
    suffix_len = requests->requestvb->name_length -
        (reginfo->rootoid_len + 1);

    for (request = requests; request; request = request->next) {
        var = request->requestvb;
        if (request->processed != 0)
            continue;

        data_context = netsnmp_extract_iterator_context(request);
        if (data_context == NULL) {
            if (reqinfo->mode == MODE_GET) {
                netsnmp_set_request_error(reqinfo, request,
                                          SNMP_NOSUCHINSTANCE);
                continue;
            }
            /** XXX: no row existed, if you support creation and this is a
               set, start dealing with it here, else continue */
        }

        /** extracts the information about the table from the request */
        table_info = netsnmp_extract_table_info(request);
        /** table_info->colnum contains the column number requested */
        /** table_info->indexes contains a linked list of snmp variable
           bindings for the indexes of the table.  Values in the list
           have been set corresponding to the indexes of the
           request */
        if (table_info == NULL) {
            continue;
        }

        switch (reqinfo->mode) {
        case MODE_GET:
            switch (table_info->colnum) {
            case COLUMN_IPCIDRROUTEDEST:
                {
                    u_long         *retval;
                    size_t          retval_len = 0;
                    retval =
                        get_ipCidrRouteDest(data_context, &retval_len);
                    snmp_set_var_typed_value(var, ASN_IPADDRESS,
                                             (const u_char *) retval,
                                             retval_len);
                }
                break;

            case COLUMN_IPCIDRROUTEMASK:
                {
                    u_long         *retval;
                    size_t          retval_len = 0;
                    retval =
                        get_ipCidrRouteMask(data_context, &retval_len);
                    snmp_set_var_typed_value(var, ASN_IPADDRESS,
                                             (const u_char *) retval,
                                             retval_len);
                }
                break;

            case COLUMN_IPCIDRROUTETOS:
                {
                    long           *retval;
                    size_t          retval_len = 0;
                    retval = get_ipCidrRouteTos(data_context, &retval_len);
                    snmp_set_var_typed_value(var, ASN_INTEGER,
                                             (const u_char *) retval,
                                             retval_len);
                }
                break;

            case COLUMN_IPCIDRROUTENEXTHOP:
                {
                    u_long         *retval;
                    size_t          retval_len = 0;
                    retval =
                        get_ipCidrRouteNextHop(data_context, &retval_len);
                    snmp_set_var_typed_value(var, ASN_IPADDRESS,
                                             (const u_char *) retval,
                                             retval_len);
                }
                break;

            case COLUMN_IPCIDRROUTEIFINDEX:
                {
                    long           *retval;
                    size_t          retval_len = 0;
                    retval =
                        get_ipCidrRouteIfIndex(data_context, &retval_len);
                    snmp_set_var_typed_value(var, ASN_INTEGER,
                                             (const u_char *) retval,
                                             retval_len);
                }
                break;

            case COLUMN_IPCIDRROUTETYPE:
                {
                    long           *retval;
                    size_t          retval_len = 0;
                    retval =
                        get_ipCidrRouteType(data_context, &retval_len);
                    snmp_set_var_typed_value(var, ASN_INTEGER,
                                             (const u_char *) retval,
                                             retval_len);
                }
                break;

            case COLUMN_IPCIDRROUTEPROTO:
                {
                    long           *retval;
                    size_t          retval_len = 0;
                    retval =
                        get_ipCidrRouteProto(data_context, &retval_len);
                    snmp_set_var_typed_value(var, ASN_INTEGER,
                                             (const u_char *) retval,
                                             retval_len);
                }
                break;

            case COLUMN_IPCIDRROUTEAGE:
                {
                    long           *retval;
                    size_t          retval_len = 0;
                    retval = get_ipCidrRouteAge(data_context, &retval_len);
                    snmp_set_var_typed_value(var, ASN_INTEGER,
                                             (const u_char *) retval,
                                             retval_len);
                }
                break;

            case COLUMN_IPCIDRROUTEINFO:
                {
                    oid            *retval;
                    size_t          retval_len = 0;
                    retval =
                        get_ipCidrRouteInfo(data_context, &retval_len);
                    snmp_set_var_typed_value(var, ASN_OBJECT_ID,
                                             (const u_char *) retval,
                                             retval_len);
                }
                break;

            case COLUMN_IPCIDRROUTENEXTHOPAS:
                {
                    long           *retval;
                    size_t          retval_len = 0;
                    retval =
                        get_ipCidrRouteNextHopAS(data_context,
                                                 &retval_len);
                    snmp_set_var_typed_value(var, ASN_INTEGER,
                                             (const u_char *) retval,
                                             retval_len);
                }
                break;

            case COLUMN_IPCIDRROUTEMETRIC1:
                {
                    long           *retval;
                    size_t          retval_len = 0;
                    retval =
                        get_ipCidrRouteMetric1(data_context, &retval_len);
                    snmp_set_var_typed_value(var, ASN_INTEGER,
                                             (const u_char *) retval,
                                             retval_len);
                }
                break;

            case COLUMN_IPCIDRROUTEMETRIC2:
                {
                    long           *retval;
                    size_t          retval_len = 0;
                    retval =
                        get_ipCidrRouteMetric2(data_context, &retval_len);
                    snmp_set_var_typed_value(var, ASN_INTEGER,
                                             (const u_char *) retval,
                                             retval_len);
                }
                break;

            case COLUMN_IPCIDRROUTEMETRIC3:
                {
                    long           *retval;
                    size_t          retval_len = 0;
                    retval =
                        get_ipCidrRouteMetric3(data_context, &retval_len);
                    snmp_set_var_typed_value(var, ASN_INTEGER,
                                             (const u_char *) retval,
                                             retval_len);
                }
                break;

            case COLUMN_IPCIDRROUTEMETRIC4:
                {
                    long           *retval;
                    size_t          retval_len = 0;
                    retval =
                        get_ipCidrRouteMetric4(data_context, &retval_len);
                    snmp_set_var_typed_value(var, ASN_INTEGER,
                                             (const u_char *) retval,
                                             retval_len);
                }
                break;

            case COLUMN_IPCIDRROUTEMETRIC5:
                {
                    long           *retval;
                    size_t          retval_len = 0;
                    retval =
                        get_ipCidrRouteMetric5(data_context, &retval_len);
                    snmp_set_var_typed_value(var, ASN_INTEGER,
                                             (const u_char *) retval,
                                             retval_len);
                }
                break;

            case COLUMN_IPCIDRROUTESTATUS:
                {
                    long           *retval;
                    size_t          retval_len = 0;
                    retval =
                        get_ipCidrRouteStatus(data_context, &retval_len);
                    snmp_set_var_typed_value(var, ASN_INTEGER,
                                             (const u_char *) retval,
                                             retval_len);
                }
                break;

            default:
                        /** We shouldn't get here */
                snmp_log(LOG_ERR,
                         "problem encountered in ipCidrRouteTable_handler: unknown column\n");
            }
            break;

        case MODE_SET_RESERVE1:
                /** mib2cXXX: clear out old undo info if we have any.  Remove if
                   table_iterator becomes un-serialized */
            netsnmp_oid_stash_free(&undoStorage, free_undoInfo);

            switch (table_info->colnum) {
            case COLUMN_IPCIDRROUTEIFINDEX:
                {
                    int             ret =
                        check_ipCidrRouteIfIndex(request->requestvb->type,
                                                 (long *) request->
                                                 requestvb->val.string,
                                                 request->requestvb->
                                                 val_len);
                    if (ret != 0) {
                        netsnmp_set_request_error(reqinfo, requests, ret);
                    }
                }
                break;
            case COLUMN_IPCIDRROUTETYPE:
                {
                    int             ret =
                        check_ipCidrRouteType(request->requestvb->type,
                                              (long *) request->requestvb->
                                              val.string,
                                              request->requestvb->val_len);
                    if (ret != 0) {
                        netsnmp_set_request_error(reqinfo, requests, ret);
                    }
                }
                break;
            case COLUMN_IPCIDRROUTEINFO:
                {
                    int             ret =
                        check_ipCidrRouteInfo(request->requestvb->type,
                                              (oid *) request->requestvb->
                                              val.string,
                                              request->requestvb->val_len);
                    if (ret != 0) {
                        netsnmp_set_request_error(reqinfo, requests, ret);
                    }
                }
                break;
            case COLUMN_IPCIDRROUTENEXTHOPAS:
                {
                    int             ret =
                        check_ipCidrRouteNextHopAS(request->requestvb->
                                                   type,
                                                   (long *) request->
                                                   requestvb->val.string,
                                                   request->requestvb->
                                                   val_len);
                    if (ret != 0) {
                        netsnmp_set_request_error(reqinfo, requests, ret);
                    }
                }
                break;
            case COLUMN_IPCIDRROUTEMETRIC1:
                {
                    int             ret =
                        check_ipCidrRouteMetric1(request->requestvb->type,
                                                 (long *) request->
                                                 requestvb->val.string,
                                                 request->requestvb->
                                                 val_len);
                    if (ret != 0) {
                        netsnmp_set_request_error(reqinfo, requests, ret);
                    }
                }
                break;
            case COLUMN_IPCIDRROUTEMETRIC2:
                {
                    int             ret =
                        check_ipCidrRouteMetric2(request->requestvb->type,
                                                 (long *) request->
                                                 requestvb->val.string,
                                                 request->requestvb->
                                                 val_len);
                    if (ret != 0) {
                        netsnmp_set_request_error(reqinfo, requests, ret);
                    }
                }
                break;
            case COLUMN_IPCIDRROUTEMETRIC3:
                {
                    int             ret =
                        check_ipCidrRouteMetric3(request->requestvb->type,
                                                 (long *) request->
                                                 requestvb->val.string,
                                                 request->requestvb->
                                                 val_len);
                    if (ret != 0) {
                        netsnmp_set_request_error(reqinfo, requests, ret);
                    }
                }
                break;
            case COLUMN_IPCIDRROUTEMETRIC4:
                {
                    int             ret =
                        check_ipCidrRouteMetric4(request->requestvb->type,
                                                 (long *) request->
                                                 requestvb->val.string,
                                                 request->requestvb->
                                                 val_len);
                    if (ret != 0) {
                        netsnmp_set_request_error(reqinfo, requests, ret);
                    }
                }
                break;
            case COLUMN_IPCIDRROUTEMETRIC5:
                {
                    int             ret =
                        check_ipCidrRouteMetric5(request->requestvb->type,
                                                 (long *) request->
                                                 requestvb->val.string,
                                                 request->requestvb->
                                                 val_len);
                    if (ret != 0) {
                        netsnmp_set_request_error(reqinfo, requests, ret);
                    }
                }
                break;
            case COLUMN_IPCIDRROUTESTATUS:
                {
                    int             ret =
                        check_ipCidrRouteStatus(request->requestvb->type,
                                                (long *) request->
                                                requestvb->val.string,
                                                request->requestvb->
                                                val_len);
                    if (ret != 0) {
                        netsnmp_set_request_error(reqinfo, requests, ret);
                    }
                }
                break;
            default:
                netsnmp_set_request_error(reqinfo, requests,
                                          SNMP_ERR_NOTWRITABLE);
                break;
            }
            break;

        case MODE_SET_RESERVE2:
                /** save a variable copy */
            switch (table_info->colnum) {
            case COLUMN_IPCIDRROUTEIFINDEX:
                {
                    long           *retval;
                    size_t          retval_len = 0;
                    struct undoInfo *ui;
                    retval =
                        get_ipCidrRouteIfIndex(data_context, &retval_len);
                    if (retval) {
                        ui = SNMP_MALLOC_STRUCT(undoInfo);
                        ui->len = retval_len;
                        memdup((u_char **) & ui->ptr,
                               (u_char *) retval, ui->len);
                        netsnmp_oid_stash_add_data(&undoStorage,
                                                   suffix, suffix_len, ui);
                    }
                }
                break;
            case COLUMN_IPCIDRROUTETYPE:
                {
                    long           *retval;
                    size_t          retval_len = 0;
                    struct undoInfo *ui;
                    retval =
                        get_ipCidrRouteType(data_context, &retval_len);
                    if (retval) {
                        ui = SNMP_MALLOC_STRUCT(undoInfo);
                        ui->len = retval_len;
                        memdup((u_char **) & ui->ptr,
                               (u_char *) retval, ui->len);
                        netsnmp_oid_stash_add_data(&undoStorage,
                                                   suffix, suffix_len, ui);
                    }
                }
                break;
            case COLUMN_IPCIDRROUTEINFO:
                {
                    oid            *retval;
                    size_t          retval_len = 0;
                    struct undoInfo *ui;
                    retval =
                        get_ipCidrRouteInfo(data_context, &retval_len);
                    if (retval) {
                        ui = SNMP_MALLOC_STRUCT(undoInfo);
                        ui->len = retval_len;
                        memdup((u_char **) & ui->ptr,
                               (u_char *) retval, ui->len);
                        netsnmp_oid_stash_add_data(&undoStorage,
                                                   suffix, suffix_len, ui);
                    }
                }
                break;
            case COLUMN_IPCIDRROUTENEXTHOPAS:
                {
                    long           *retval;
                    size_t          retval_len = 0;
                    struct undoInfo *ui;
                    retval =
                        get_ipCidrRouteNextHopAS(data_context,
                                                 &retval_len);
                    if (retval) {
                        ui = SNMP_MALLOC_STRUCT(undoInfo);
                        ui->len = retval_len;
                        memdup((u_char **) & ui->ptr,
                               (u_char *) retval, ui->len);
                        netsnmp_oid_stash_add_data(&undoStorage,
                                                   suffix, suffix_len, ui);
                    }
                }
                break;
            case COLUMN_IPCIDRROUTEMETRIC1:
                {
                    long           *retval;
                    size_t          retval_len = 0;
                    struct undoInfo *ui;
                    retval =
                        get_ipCidrRouteMetric1(data_context, &retval_len);
                    if (retval) {
                        ui = SNMP_MALLOC_STRUCT(undoInfo);
                        ui->len = retval_len;
                        memdup((u_char **) & ui->ptr,
                               (u_char *) retval, ui->len);
                        netsnmp_oid_stash_add_data(&undoStorage,
                                                   suffix, suffix_len, ui);
                    }
                }
                break;
            case COLUMN_IPCIDRROUTEMETRIC2:
                {
                    long           *retval;
                    size_t          retval_len = 0;
                    struct undoInfo *ui;
                    retval =
                        get_ipCidrRouteMetric2(data_context, &retval_len);
                    if (retval) {
                        ui = SNMP_MALLOC_STRUCT(undoInfo);
                        ui->len = retval_len;
                        memdup((u_char **) & ui->ptr,
                               (u_char *) retval, ui->len);
                        netsnmp_oid_stash_add_data(&undoStorage,
                                                   suffix, suffix_len, ui);
                    }
                }
                break;
            case COLUMN_IPCIDRROUTEMETRIC3:
                {
                    long           *retval;
                    size_t          retval_len = 0;
                    struct undoInfo *ui;
                    retval =
                        get_ipCidrRouteMetric3(data_context, &retval_len);
                    if (retval) {
                        ui = SNMP_MALLOC_STRUCT(undoInfo);
                        ui->len = retval_len;
                        memdup((u_char **) & ui->ptr,
                               (u_char *) retval, ui->len);
                        netsnmp_oid_stash_add_data(&undoStorage,
                                                   suffix, suffix_len, ui);
                    }
                }
                break;
            case COLUMN_IPCIDRROUTEMETRIC4:
                {
                    long           *retval;
                    size_t          retval_len = 0;
                    struct undoInfo *ui;
                    retval =
                        get_ipCidrRouteMetric4(data_context, &retval_len);
                    if (retval) {
                        ui = SNMP_MALLOC_STRUCT(undoInfo);
                        ui->len = retval_len;
                        memdup((u_char **) & ui->ptr,
                               (u_char *) retval, ui->len);
                        netsnmp_oid_stash_add_data(&undoStorage,
                                                   suffix, suffix_len, ui);
                    }
                }
                break;
            case COLUMN_IPCIDRROUTEMETRIC5:
                {
                    long           *retval;
                    size_t          retval_len = 0;
                    struct undoInfo *ui;
                    retval =
                        get_ipCidrRouteMetric5(data_context, &retval_len);
                    if (retval) {
                        ui = SNMP_MALLOC_STRUCT(undoInfo);
                        ui->len = retval_len;
                        memdup((u_char **) & ui->ptr,
                               (u_char *) retval, ui->len);
                        netsnmp_oid_stash_add_data(&undoStorage,
                                                   suffix, suffix_len, ui);
                    }
                }
                break;
            case COLUMN_IPCIDRROUTESTATUS:
                {
                    long           *retval;
                    size_t          retval_len = 0;
                    struct undoInfo *ui;
                    retval =
                        get_ipCidrRouteStatus(data_context, &retval_len);
                    if (retval) {
                        ui = SNMP_MALLOC_STRUCT(undoInfo);
                        ui->len = retval_len;
                        memdup((u_char **) & ui->ptr,
                               (u_char *) retval, ui->len);
                        netsnmp_oid_stash_add_data(&undoStorage,
                                                   suffix, suffix_len, ui);
                    }
                }
                break;
            }
            break;

        case MODE_SET_FREE:
                /** Forget undo data, if exists */
            netsnmp_oid_stash_free(&undoStorage, free_undoInfo);
            break;

        case MODE_SET_ACTION:
                /** save a variable copy */
            switch (table_info->colnum) {
            case COLUMN_IPCIDRROUTEIFINDEX:
                {
                    int             ret =
                        set_ipCidrRouteIfIndex(data_context,
                                               (long *) request->
                                               requestvb->val.string,
                                               request->requestvb->
                                               val_len);
                    if (ret) {
                        netsnmp_set_request_error(reqinfo, requests, ret);
                    }
                }
                break;
            case COLUMN_IPCIDRROUTETYPE:
                {
                    int             ret = set_ipCidrRouteType(data_context,
                                                              (long *)
                                                              request->
                                                              requestvb->
                                                              val.string,
                                                              request->
                                                              requestvb->
                                                              val_len);
                    if (ret) {
                        netsnmp_set_request_error(reqinfo, requests, ret);
                    }
                }
                break;
            case COLUMN_IPCIDRROUTEINFO:
                {
                    int             ret = set_ipCidrRouteInfo(data_context,
                                                              (oid *)
                                                              request->
                                                              requestvb->
                                                              val.string,
                                                              request->
                                                              requestvb->
                                                              val_len);
                    if (ret) {
                        netsnmp_set_request_error(reqinfo, requests, ret);
                    }
                }
                break;
            case COLUMN_IPCIDRROUTENEXTHOPAS:
                {
                    int             ret =
                        set_ipCidrRouteNextHopAS(data_context,
                                                 (long *) request->
                                                 requestvb->val.string,
                                                 request->requestvb->
                                                 val_len);
                    if (ret) {
                        netsnmp_set_request_error(reqinfo, requests, ret);
                    }
                }
                break;
            case COLUMN_IPCIDRROUTEMETRIC1:
                {
                    int             ret =
                        set_ipCidrRouteMetric1(data_context,
                                               (long *) request->
                                               requestvb->val.string,
                                               request->requestvb->
                                               val_len);
                    if (ret) {
                        netsnmp_set_request_error(reqinfo, requests, ret);
                    }
                }
                break;
            case COLUMN_IPCIDRROUTEMETRIC2:
                {
                    int             ret =
                        set_ipCidrRouteMetric2(data_context,
                                               (long *) request->
                                               requestvb->val.string,
                                               request->requestvb->
                                               val_len);
                    if (ret) {
                        netsnmp_set_request_error(reqinfo, requests, ret);
                    }
                }
                break;
            case COLUMN_IPCIDRROUTEMETRIC3:
                {
                    int             ret =
                        set_ipCidrRouteMetric3(data_context,
                                               (long *) request->
                                               requestvb->val.string,
                                               request->requestvb->
                                               val_len);
                    if (ret) {
                        netsnmp_set_request_error(reqinfo, requests, ret);
                    }
                }
                break;
            case COLUMN_IPCIDRROUTEMETRIC4:
                {
                    int             ret =
                        set_ipCidrRouteMetric4(data_context,
                                               (long *) request->
                                               requestvb->val.string,
                                               request->requestvb->
                                               val_len);
                    if (ret) {
                        netsnmp_set_request_error(reqinfo, requests, ret);
                    }
                }
                break;
            case COLUMN_IPCIDRROUTEMETRIC5:
                {
                    int             ret =
                        set_ipCidrRouteMetric5(data_context,
                                               (long *) request->
                                               requestvb->val.string,
                                               request->requestvb->
                                               val_len);
                    if (ret) {
                        netsnmp_set_request_error(reqinfo, requests, ret);
                    }
                }
                break;
            case COLUMN_IPCIDRROUTESTATUS:
                {
                    int             ret =
                        set_ipCidrRouteStatus(data_context,
                                              (long *) request->requestvb->
                                              val.string,
                                              request->requestvb->val_len);
                    if (ret) {
                        netsnmp_set_request_error(reqinfo, requests, ret);
                    }
                }
                break;
            }
            break;

        case MODE_SET_COMMIT:
                /** answers were all good.  Forget undo data */
            netsnmp_oid_stash_free(&undoStorage, free_undoInfo);
                /** mib2cXXX: call commit hook */
            break;

        case MODE_SET_UNDO:
                /** save a variable copy */
            switch (table_info->colnum) {
            case COLUMN_IPCIDRROUTEIFINDEX:
                {
                    int             retval;
                    struct undoInfo *ui;
                    ui = netsnmp_oid_stash_get_data(undoStorage,
                                                    suffix, suffix_len);
                    retval =
                        set_ipCidrRouteIfIndex(data_context, ui->ptr,
                                               ui->len);
                    if (retval) {
                        netsnmp_set_request_error(reqinfo, requests,
                                                  SNMP_ERR_UNDOFAILED);
                    }
                }
                break;
            case COLUMN_IPCIDRROUTETYPE:
                {
                    int             retval;
                    struct undoInfo *ui;
                    ui = netsnmp_oid_stash_get_data(undoStorage,
                                                    suffix, suffix_len);
                    retval =
                        set_ipCidrRouteType(data_context, ui->ptr,
                                            ui->len);
                    if (retval) {
                        netsnmp_set_request_error(reqinfo, requests,
                                                  SNMP_ERR_UNDOFAILED);
                    }
                }
                break;
            case COLUMN_IPCIDRROUTEINFO:
                {
                    int             retval;
                    struct undoInfo *ui;
                    ui = netsnmp_oid_stash_get_data(undoStorage,
                                                    suffix, suffix_len);
                    retval =
                        set_ipCidrRouteInfo(data_context, ui->ptr,
                                            ui->len);
                    if (retval) {
                        netsnmp_set_request_error(reqinfo, requests,
                                                  SNMP_ERR_UNDOFAILED);
                    }
                }
                break;
            case COLUMN_IPCIDRROUTENEXTHOPAS:
                {
                    int             retval;
                    struct undoInfo *ui;
                    ui = netsnmp_oid_stash_get_data(undoStorage,
                                                    suffix, suffix_len);
                    retval =
                        set_ipCidrRouteNextHopAS(data_context, ui->ptr,
                                                 ui->len);
                    if (retval) {
                        netsnmp_set_request_error(reqinfo, requests,
                                                  SNMP_ERR_UNDOFAILED);
                    }
                }
                break;
            case COLUMN_IPCIDRROUTEMETRIC1:
                {
                    int             retval;
                    struct undoInfo *ui;
                    ui = netsnmp_oid_stash_get_data(undoStorage,
                                                    suffix, suffix_len);
                    retval =
                        set_ipCidrRouteMetric1(data_context, ui->ptr,
                                               ui->len);
                    if (retval) {
                        netsnmp_set_request_error(reqinfo, requests,
                                                  SNMP_ERR_UNDOFAILED);
                    }
                }
                break;
            case COLUMN_IPCIDRROUTEMETRIC2:
                {
                    int             retval;
                    struct undoInfo *ui;
                    ui = netsnmp_oid_stash_get_data(undoStorage,
                                                    suffix, suffix_len);
                    retval =
                        set_ipCidrRouteMetric2(data_context, ui->ptr,
                                               ui->len);
                    if (retval) {
                        netsnmp_set_request_error(reqinfo, requests,
                                                  SNMP_ERR_UNDOFAILED);
                    }
                }
                break;
            case COLUMN_IPCIDRROUTEMETRIC3:
                {
                    int             retval;
                    struct undoInfo *ui;
                    ui = netsnmp_oid_stash_get_data(undoStorage,
                                                    suffix, suffix_len);
                    retval =
                        set_ipCidrRouteMetric3(data_context, ui->ptr,
                                               ui->len);
                    if (retval) {
                        netsnmp_set_request_error(reqinfo, requests,
                                                  SNMP_ERR_UNDOFAILED);
                    }
                }
                break;
            case COLUMN_IPCIDRROUTEMETRIC4:
                {
                    int             retval;
                    struct undoInfo *ui;
                    ui = netsnmp_oid_stash_get_data(undoStorage,
                                                    suffix, suffix_len);
                    retval =
                        set_ipCidrRouteMetric4(data_context, ui->ptr,
                                               ui->len);
                    if (retval) {
                        netsnmp_set_request_error(reqinfo, requests,
                                                  SNMP_ERR_UNDOFAILED);
                    }
                }
                break;
            case COLUMN_IPCIDRROUTEMETRIC5:
                {
                    int             retval;
                    struct undoInfo *ui;
                    ui = netsnmp_oid_stash_get_data(undoStorage,
                                                    suffix, suffix_len);
                    retval =
                        set_ipCidrRouteMetric5(data_context, ui->ptr,
                                               ui->len);
                    if (retval) {
                        netsnmp_set_request_error(reqinfo, requests,
                                                  SNMP_ERR_UNDOFAILED);
                    }
                }
                break;
            case COLUMN_IPCIDRROUTESTATUS:
                {
                    int             retval;
                    struct undoInfo *ui;
                    ui = netsnmp_oid_stash_get_data(undoStorage,
                                                    suffix, suffix_len);
                    retval =
                        set_ipCidrRouteStatus(data_context, ui->ptr,
                                              ui->len);
                    if (retval) {
                        netsnmp_set_request_error(reqinfo, requests,
                                                  SNMP_ERR_UNDOFAILED);
                    }
                }
                break;
            }
                /** mib2cXXX: remove cache!  hard to do when serialized, however */
            break;

        default:
            snmp_log(LOG_ERR,
                     "problem encountered in ipCidrRouteTable_handler: unsupported mode\n");
        }
    }
    return SNMP_ERR_NOERROR;
}
/** handles requests for the nsTransactionTable table, if anything
   else needs to be done */
int
nsTransactionTable_handler(netsnmp_mib_handler *handler,
                           netsnmp_handler_registration *reginfo,
                           netsnmp_agent_request_info *reqinfo,
                           netsnmp_request_info *requests)
{

    netsnmp_table_request_info *table_info;
    netsnmp_variable_list *var;
    netsnmp_agent_session *asp;

    for (; requests; requests = requests->next) {
        var = requests->requestvb;
        if (requests->processed != 0)
            continue;

        /*
         * perform anything here that you need to do.  The requests have
         * already been processed by the master table_dataset handler, but
         * this gives you chance to act on the request in some other way if 
         * need be. 
         */

        /*
         * the following extracts the my_data_context pointer set in the
         * loop functions above.  You can then use the results to help
         * return data for the columns of the nsTransactionTable table in
         * question 
         */
        asp =
            (netsnmp_agent_session *)
            netsnmp_extract_iterator_context(requests);
        if (asp == NULL) {
            netsnmp_set_request_error(reqinfo, requests,
                                      SNMP_NOSUCHINSTANCE);
        }

        /*
         * extracts the information about the table from the request 
         */
        table_info = netsnmp_extract_table_info(requests);

        /*
         * table_info->colnum contains the column number requested 
         */
        /*
         * table_info->indexes contains a linked list of snmp variable
         * bindings for the indexes of the table.  Values in the list have 
         * been set corresponding to the indexes of the request 
         */
        if (table_info == NULL) {
            continue;
        }

        switch (reqinfo->mode) {
            /*
             * the table_iterator helper should change all GETNEXTs into
             * GETs for you automatically, so you don't have to worry
             * about the GETNEXT case.  Only GETs and SETs need to be
             * dealt with here 
             */
        case MODE_GET:
            switch (table_info->colnum) {

            case COLUMN_NSTRANSACTIONMODE:
                snmp_set_var_typed_value(var, ASN_INTEGER,
                                         (u_char *) & asp->mode,
                                         sizeof(asp->mode));
                break;

            default:
                /*
                 * We shouldn't get here 
                 */
                snmp_log(LOG_ERR,
                         "problem encountered in nsTransactionTable_handler: unknown column\n");
            }
            break;

        default:
            snmp_log(LOG_ERR,
                     "problem encountered in nsTransactionTable_handler: unsupported mode\n");
        }
    }
    return SNMP_ERR_NOERROR;
}
int
handle_shutdown(netsnmp_mib_handler *handler,
                          netsnmp_handler_registration *reginfo,
                          netsnmp_agent_request_info   *reqinfo,
                          netsnmp_request_info         *requests)
{
    int ret;
    /* We are never called for a GETNEXT if it's registered as a
       "instance", as it's "magically" handled for us.  */

    /* a instance handler also only hands us one request at a time, so
       we don't need to loop over a list of requests; we'll only get one. */

    switch(reqinfo->mode) {

        case MODE_GET:
            netsnmp_set_request_error(reqinfo, requests, SNMP_NOSUCHINSTANCE );
            break;

        /*
         * SET REQUEST
         *
         * multiple states in the transaction.  See:
         * http://www.net-snmp.org/tutorial-5/toolkit/mib_module/set-actions.jpg
         */
        case MODE_SET_RESERVE1:
                /* or you could use netsnmp_check_vb_type_and_size instead */
            ret = netsnmp_check_vb_type(requests->requestvb, ASN_INTEGER);
            if ( ret != SNMP_ERR_NOERROR ) {
                netsnmp_set_request_error(reqinfo, requests, ret );
            }
            break;

        case MODE_SET_RESERVE2:
            /* XXX malloc "undo" storage buffer */
            break;

        case MODE_SET_FREE:
            /* XXX: free resources allocated in RESERVE1 and/or
               RESERVE2.  Something failed somewhere, and the states
               below won't be called. */
            break;

        case MODE_SET_ACTION:
            /* XXX: perform the value change here */
            break;

        case MODE_SET_COMMIT:
            /* XXX: delete temporary storage */
            break;

        case MODE_SET_UNDO:
            /* XXX: UNDO and return to previous value for the object */
            break;

        default:
            /* we should never get here, so this is a really bad error */
            snmp_log(LOG_ERR, "unknown mode (%d) in handle_shutdown\n", reqinfo->mode );
            return SNMP_ERR_GENERR;
    }

    return SNMP_ERR_NOERROR;
}