A version of LWIP, provided for backwards compatibility.

Dependents:   AA_DemoBoard DemoBoard HelloServerDemo DemoBoard_RangeIndicator ... more

Embed: (wiki syntax)

« Back to documentation index

Show/hide line numbers mib2.c Source File

mib2.c

Go to the documentation of this file.
00001 /**
00002  * @file
00003  * Management Information Base II (RFC1213) objects and functions.
00004  *
00005  * @note the object identifiers for this MIB-2 and private MIB tree
00006  * must be kept in sorted ascending order. This to ensure correct getnext operation.
00007  */
00008 
00009 /*
00010  * Copyright (c) 2006 Axon Digital Design B.V., The Netherlands.
00011  * All rights reserved.
00012  *
00013  * Redistribution and use in source and binary forms, with or without modification,
00014  * are permitted provided that the following conditions are met:
00015  *
00016  * 1. Redistributions of source code must retain the above copyright notice,
00017  *    this list of conditions and the following disclaimer.
00018  * 2. Redistributions in binary form must reproduce the above copyright notice,
00019  *    this list of conditions and the following disclaimer in the documentation
00020  *    and/or other materials provided with the distribution.
00021  * 3. The name of the author may not be used to endorse or promote products
00022  *    derived from this software without specific prior written permission.
00023  *
00024  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR IMPLIED
00025  * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
00026  * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT
00027  * SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
00028  * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT
00029  * OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
00030  * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
00031  * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING
00032  * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY
00033  * OF SUCH DAMAGE.
00034  *
00035  * Author: Christiaan Simons <christiaan.simons@axon.tv>
00036  */
00037 
00038 #include "lwip/opt.h"
00039 
00040 #if LWIP_SNMP /* don't build if not configured for use in lwipopts.h */
00041 
00042 #include "lwip/snmp.h"
00043 #include "lwip/netif.h"
00044 #include "lwip/ip.h"
00045 #include "lwip/ip_frag.h"
00046 #include "lwip/tcp.h"
00047 #include "lwip/udp.h"
00048 #include "lwip/snmp_asn1.h"
00049 #include "lwip/snmp_structs.h"
00050 #include "netif/etharp.h"
00051 
00052 /**
00053  * IANA assigned enterprise ID for lwIP is 26381
00054  * @see http://www.iana.org/assignments/enterprise-numbers
00055  *
00056  * @note this enterprise ID is assigned to the lwIP project,
00057  * all object identifiers living under this ID are assigned
00058  * by the lwIP maintainers (contact Christiaan Simons)!
00059  * @note don't change this define, use snmp_set_sysobjid()
00060  *
00061  * If you need to create your own private MIB you'll need
00062  * to apply for your own enterprise ID with IANA:
00063  * http://www.iana.org/numbers.html
00064  */
00065 #define SNMP_ENTERPRISE_ID 26381
00066 #define SNMP_SYSOBJID_LEN 7
00067 #define SNMP_SYSOBJID {1, 3, 6, 1, 4, 1, SNMP_ENTERPRISE_ID}
00068 
00069 #ifndef SNMP_SYSSERVICES
00070 #define SNMP_SYSSERVICES ((1 << 6) | (1 << 3) | ((IP_FORWARD) << 2))
00071 #endif
00072 
00073 #ifndef SNMP_GET_SYSUPTIME
00074 #define SNMP_GET_SYSUPTIME(sysuptime)
00075 #endif
00076 
00077 static void system_get_object_def(u8_t ident_len, s32_t *ident, struct obj_def *od);
00078 static void system_get_value(struct obj_def *od, u16_t len, void *value);
00079 static u8_t system_set_test(struct obj_def *od, u16_t len, void *value);
00080 static void system_set_value(struct obj_def *od, u16_t len, void *value);
00081 static void interfaces_get_object_def(u8_t ident_len, s32_t *ident, struct obj_def *od);
00082 static void interfaces_get_value(struct obj_def *od, u16_t len, void *value);
00083 static void ifentry_get_object_def(u8_t ident_len, s32_t *ident, struct obj_def *od);
00084 static void ifentry_get_value(struct obj_def *od, u16_t len, void *value);
00085 #if !SNMP_SAFE_REQUESTS
00086 static u8_t ifentry_set_test (struct obj_def *od, u16_t len, void *value);
00087 static void ifentry_set_value (struct obj_def *od, u16_t len, void *value);
00088 #endif /* SNMP_SAFE_REQUESTS */
00089 static void atentry_get_object_def(u8_t ident_len, s32_t *ident, struct obj_def *od);
00090 static void atentry_get_value(struct obj_def *od, u16_t len, void *value);
00091 static void ip_get_object_def(u8_t ident_len, s32_t *ident, struct obj_def *od);
00092 static void ip_get_value (struct obj_def *od, u16_t len, void *value);
00093 static u8_t ip_set_test(struct obj_def *od, u16_t len, void *value);
00094 static void ip_addrentry_get_object_def(u8_t ident_len, s32_t *ident, struct obj_def *od);
00095 static void ip_addrentry_get_value (struct obj_def *od, u16_t len, void *value);
00096 static void ip_rteentry_get_object_def (u8_t ident_len, s32_t *ident, struct obj_def *od);
00097 static void ip_rteentry_get_value (struct obj_def *od, u16_t len, void *value);
00098 static void ip_ntomentry_get_object_def (u8_t ident_len, s32_t *ident, struct obj_def *od);
00099 static void ip_ntomentry_get_value(struct obj_def *od, u16_t len, void *value);
00100 static void icmp_get_object_def(u8_t ident_len, s32_t *ident, struct obj_def *od);
00101 static void icmp_get_value(struct obj_def *od, u16_t len, void *value);
00102 #if LWIP_TCP
00103 static void tcp_get_object_def (u8_t ident_len, s32_t *ident, struct obj_def *od);
00104 static void tcp_get_value(struct obj_def *od, u16_t len, void *value);
00105 #ifdef THIS_SEEMS_UNUSED
00106 static void tcpconnentry_get_object_def(u8_t ident_len, s32_t *ident, struct obj_def *od);
00107 static void tcpconnentry_get_value (struct obj_def *od, u16_t len, void *value);
00108 #endif
00109 #endif
00110 static void udp_get_object_def(u8_t ident_len, s32_t *ident, struct obj_def *od);
00111 static void udp_get_value(struct obj_def *od, u16_t len, void *value);
00112 static void udpentry_get_object_def(u8_t ident_len, s32_t *ident, struct obj_def *od);
00113 static void udpentry_get_value(struct obj_def *od, u16_t len, void *value);
00114 static void snmp_get_object_def(u8_t ident_len, s32_t *ident, struct obj_def *od);
00115 static void snmp_get_value(struct obj_def *od, u16_t len, void *value);
00116 static u8_t snmp_set_test(struct obj_def *od, u16_t len, void *value);
00117 static void snmp_set_value(struct obj_def *od, u16_t len, void *value);
00118 
00119 
00120 /* snmp .1.3.6.1.2.1.11 */
00121 const mib_scalar_node snmp_scalar = {
00122   &snmp_get_object_def,
00123   &snmp_get_value,
00124   &snmp_set_test,
00125   &snmp_set_value,
00126   MIB_NODE_SC,
00127   0
00128 };
00129 const s32_t snmp_ids[28] = {
00130   1, 2, 3, 4, 5, 6, 8, 9, 10, 11, 12, 13, 14, 15, 16,
00131   17, 18, 19, 20, 21, 22, 24, 25, 26, 27, 28, 29, 30
00132 };
00133 struct mib_node* const snmp_nodes[28] = {
00134   (struct mib_node* const)&snmp_scalar, (struct mib_node* const)&snmp_scalar,
00135   (struct mib_node* const)&snmp_scalar, (struct mib_node* const)&snmp_scalar,
00136   (struct mib_node* const)&snmp_scalar, (struct mib_node* const)&snmp_scalar,
00137   (struct mib_node* const)&snmp_scalar, (struct mib_node* const)&snmp_scalar,
00138   (struct mib_node* const)&snmp_scalar, (struct mib_node* const)&snmp_scalar,
00139   (struct mib_node* const)&snmp_scalar, (struct mib_node* const)&snmp_scalar,
00140   (struct mib_node* const)&snmp_scalar, (struct mib_node* const)&snmp_scalar,
00141   (struct mib_node* const)&snmp_scalar, (struct mib_node* const)&snmp_scalar,
00142   (struct mib_node* const)&snmp_scalar, (struct mib_node* const)&snmp_scalar,
00143   (struct mib_node* const)&snmp_scalar, (struct mib_node* const)&snmp_scalar,
00144   (struct mib_node* const)&snmp_scalar, (struct mib_node* const)&snmp_scalar,
00145   (struct mib_node* const)&snmp_scalar, (struct mib_node* const)&snmp_scalar,
00146   (struct mib_node* const)&snmp_scalar, (struct mib_node* const)&snmp_scalar,
00147   (struct mib_node* const)&snmp_scalar, (struct mib_node* const)&snmp_scalar
00148 };
00149 const struct mib_array_node snmp = {
00150   &noleafs_get_object_def,
00151   &noleafs_get_value,
00152   &noleafs_set_test,
00153   &noleafs_set_value,
00154   MIB_NODE_AR,
00155   28,
00156   snmp_ids,
00157   snmp_nodes
00158 };
00159 
00160 /* dot3 and EtherLike MIB not planned. (transmission .1.3.6.1.2.1.10) */
00161 /* historical (some say hysterical). (cmot .1.3.6.1.2.1.9) */
00162 /* lwIP has no EGP, thus may not implement it. (egp .1.3.6.1.2.1.8) */
00163 
00164 /* udp .1.3.6.1.2.1.7 */
00165 /** index root node for udpTable */
00166 struct mib_list_rootnode udp_root = {
00167   &noleafs_get_object_def,
00168   &noleafs_get_value,
00169   &noleafs_set_test,
00170   &noleafs_set_value,
00171   MIB_NODE_LR,
00172   0,
00173   NULL,
00174   NULL,
00175   0
00176 };
00177 const s32_t udpentry_ids[2] = { 1, 2 };
00178 struct mib_node* const udpentry_nodes[2] = {
00179   (struct mib_node* const)&udp_root, (struct mib_node* const)&udp_root,
00180 };
00181 const struct mib_array_node udpentry = {
00182   &noleafs_get_object_def,
00183   &noleafs_get_value,
00184   &noleafs_set_test,
00185   &noleafs_set_value,
00186   MIB_NODE_AR,
00187   2,
00188   udpentry_ids,
00189   udpentry_nodes
00190 };
00191 
00192 s32_t udptable_id = 1;
00193 struct mib_node* udptable_node = (struct mib_node* const)&udpentry;
00194 struct mib_ram_array_node udptable = {
00195   &noleafs_get_object_def,
00196   &noleafs_get_value,
00197   &noleafs_set_test,
00198   &noleafs_set_value,
00199   MIB_NODE_RA,
00200   0,
00201   &udptable_id,
00202   &udptable_node
00203 };
00204 
00205 const mib_scalar_node udp_scalar = {
00206   &udp_get_object_def,
00207   &udp_get_value,
00208   &noleafs_set_test,
00209   &noleafs_set_value,
00210   MIB_NODE_SC,
00211   0
00212 };
00213 const s32_t udp_ids[5] = { 1, 2, 3, 4, 5 };
00214 struct mib_node* const udp_nodes[5] = {
00215   (struct mib_node* const)&udp_scalar, (struct mib_node* const)&udp_scalar,
00216   (struct mib_node* const)&udp_scalar, (struct mib_node* const)&udp_scalar,
00217   (struct mib_node* const)&udptable
00218 };
00219 const struct mib_array_node udp = {
00220   &noleafs_get_object_def,
00221   &noleafs_get_value,
00222   &noleafs_set_test,
00223   &noleafs_set_value,
00224   MIB_NODE_AR,
00225   5,
00226   udp_ids,
00227   udp_nodes
00228 };
00229 
00230 /* tcp .1.3.6.1.2.1.6 */
00231 #if LWIP_TCP
00232 /* only if the TCP protocol is available may implement this group */
00233 /** index root node for tcpConnTable */
00234 struct mib_list_rootnode tcpconntree_root = {
00235   &noleafs_get_object_def,
00236   &noleafs_get_value,
00237   &noleafs_set_test,
00238   &noleafs_set_value,
00239   MIB_NODE_LR,
00240   0,
00241   NULL,
00242   NULL,
00243   0
00244 };
00245 const s32_t tcpconnentry_ids[5] = { 1, 2, 3, 4, 5 };
00246 struct mib_node* const tcpconnentry_nodes[5] = {
00247   (struct mib_node* const)&tcpconntree_root, (struct mib_node* const)&tcpconntree_root,
00248   (struct mib_node* const)&tcpconntree_root, (struct mib_node* const)&tcpconntree_root,
00249   (struct mib_node* const)&tcpconntree_root
00250 };
00251 const struct mib_array_node tcpconnentry = {
00252   &noleafs_get_object_def,
00253   &noleafs_get_value,
00254   &noleafs_set_test,
00255   &noleafs_set_value,
00256   MIB_NODE_AR,
00257   5,
00258   tcpconnentry_ids,
00259   tcpconnentry_nodes
00260 };
00261 
00262 s32_t tcpconntable_id = 1;
00263 struct mib_node* tcpconntable_node = (struct mib_node* const)&tcpconnentry;
00264 struct mib_ram_array_node tcpconntable = {
00265   &noleafs_get_object_def,
00266   &noleafs_get_value,
00267   &noleafs_set_test,
00268   &noleafs_set_value,
00269   MIB_NODE_RA,
00270 /** @todo update maxlength when inserting / deleting from table
00271    0 when table is empty, 1 when more than one entry */
00272   0,
00273   &tcpconntable_id,
00274   &tcpconntable_node
00275 };
00276 
00277 const mib_scalar_node tcp_scalar = {
00278   &tcp_get_object_def ,
00279   &tcp_get_value,
00280   &noleafs_set_test,
00281   &noleafs_set_value,
00282   MIB_NODE_SC,
00283   0
00284 };
00285 const s32_t tcp_ids[15] = { 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15 };
00286 struct mib_node* const tcp_nodes[15] = {
00287   (struct mib_node* const)&tcp_scalar, (struct mib_node* const)&tcp_scalar,
00288   (struct mib_node* const)&tcp_scalar, (struct mib_node* const)&tcp_scalar,
00289   (struct mib_node* const)&tcp_scalar, (struct mib_node* const)&tcp_scalar,
00290   (struct mib_node* const)&tcp_scalar, (struct mib_node* const)&tcp_scalar,
00291   (struct mib_node* const)&tcp_scalar, (struct mib_node* const)&tcp_scalar,
00292   (struct mib_node* const)&tcp_scalar, (struct mib_node* const)&tcp_scalar,
00293   (struct mib_node* const)&tcpconntable, (struct mib_node* const)&tcp_scalar,
00294   (struct mib_node* const)&tcp_scalar
00295 };
00296 const struct mib_array_node tcp = {
00297   &noleafs_get_object_def,
00298   &noleafs_get_value,
00299   &noleafs_set_test,
00300   &noleafs_set_value,
00301   MIB_NODE_AR,
00302   15,
00303   tcp_ids,
00304   tcp_nodes
00305 };
00306 #endif
00307 
00308 /* icmp .1.3.6.1.2.1.5 */
00309 const mib_scalar_node icmp_scalar = {
00310   &icmp_get_object_def,
00311   &icmp_get_value,
00312   &noleafs_set_test,
00313   &noleafs_set_value,
00314   MIB_NODE_SC,
00315   0
00316 };
00317 const s32_t icmp_ids[26] = { 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24, 25, 26 };
00318 struct mib_node* const icmp_nodes[26] = {
00319   (struct mib_node* const)&icmp_scalar, (struct mib_node* const)&icmp_scalar,
00320   (struct mib_node* const)&icmp_scalar, (struct mib_node* const)&icmp_scalar,
00321   (struct mib_node* const)&icmp_scalar, (struct mib_node* const)&icmp_scalar,
00322   (struct mib_node* const)&icmp_scalar, (struct mib_node* const)&icmp_scalar,
00323   (struct mib_node* const)&icmp_scalar, (struct mib_node* const)&icmp_scalar,
00324   (struct mib_node* const)&icmp_scalar, (struct mib_node* const)&icmp_scalar,
00325   (struct mib_node* const)&icmp_scalar, (struct mib_node* const)&icmp_scalar,
00326   (struct mib_node* const)&icmp_scalar, (struct mib_node* const)&icmp_scalar,
00327   (struct mib_node* const)&icmp_scalar, (struct mib_node* const)&icmp_scalar,
00328   (struct mib_node* const)&icmp_scalar, (struct mib_node* const)&icmp_scalar,
00329   (struct mib_node* const)&icmp_scalar, (struct mib_node* const)&icmp_scalar,
00330   (struct mib_node* const)&icmp_scalar, (struct mib_node* const)&icmp_scalar,
00331   (struct mib_node* const)&icmp_scalar, (struct mib_node* const)&icmp_scalar
00332 };
00333 const struct mib_array_node icmp = {
00334   &noleafs_get_object_def,
00335   &noleafs_get_value,
00336   &noleafs_set_test,
00337   &noleafs_set_value,
00338   MIB_NODE_AR,
00339   26,
00340   icmp_ids,
00341   icmp_nodes
00342 };
00343 
00344 /** index root node for ipNetToMediaTable */
00345 struct mib_list_rootnode ipntomtree_root = {
00346   &noleafs_get_object_def,
00347   &noleafs_get_value,
00348   &noleafs_set_test,
00349   &noleafs_set_value,
00350   MIB_NODE_LR,
00351   0,
00352   NULL,
00353   NULL,
00354   0
00355 };
00356 const s32_t ipntomentry_ids[4] = { 1, 2, 3, 4 };
00357 struct mib_node* const ipntomentry_nodes[4] = {
00358   (struct mib_node* const)&ipntomtree_root, (struct mib_node* const)&ipntomtree_root,
00359   (struct mib_node* const)&ipntomtree_root, (struct mib_node* const)&ipntomtree_root
00360 };
00361 const struct mib_array_node ipntomentry = {
00362   &noleafs_get_object_def,
00363   &noleafs_get_value,
00364   &noleafs_set_test,
00365   &noleafs_set_value,
00366   MIB_NODE_AR,
00367   4,
00368   ipntomentry_ids,
00369   ipntomentry_nodes
00370 };
00371 
00372 s32_t ipntomtable_id = 1;
00373 struct mib_node* ipntomtable_node = (struct mib_node* const)&ipntomentry;
00374 struct mib_ram_array_node ipntomtable = {
00375   &noleafs_get_object_def,
00376   &noleafs_get_value,
00377   &noleafs_set_test,
00378   &noleafs_set_value,
00379   MIB_NODE_RA,
00380   0,
00381   &ipntomtable_id,
00382   &ipntomtable_node
00383 };
00384 
00385 /** index root node for ipRouteTable */
00386 struct mib_list_rootnode iprtetree_root = {
00387   &noleafs_get_object_def,
00388   &noleafs_get_value,
00389   &noleafs_set_test,
00390   &noleafs_set_value,
00391   MIB_NODE_LR,
00392   0,
00393   NULL,
00394   NULL,
00395   0
00396 };
00397 const s32_t iprteentry_ids[13] = { 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13 };
00398 struct mib_node* const iprteentry_nodes[13] = {
00399   (struct mib_node* const)&iprtetree_root, (struct mib_node* const)&iprtetree_root,
00400   (struct mib_node* const)&iprtetree_root, (struct mib_node* const)&iprtetree_root,
00401   (struct mib_node* const)&iprtetree_root, (struct mib_node* const)&iprtetree_root,
00402   (struct mib_node* const)&iprtetree_root, (struct mib_node* const)&iprtetree_root,
00403   (struct mib_node* const)&iprtetree_root, (struct mib_node* const)&iprtetree_root,
00404   (struct mib_node* const)&iprtetree_root, (struct mib_node* const)&iprtetree_root,
00405   (struct mib_node* const)&iprtetree_root
00406 };
00407 const struct mib_array_node iprteentry = {
00408   &noleafs_get_object_def,
00409   &noleafs_get_value,
00410   &noleafs_set_test,
00411   &noleafs_set_value,
00412   MIB_NODE_AR,
00413   13,
00414   iprteentry_ids,
00415   iprteentry_nodes
00416 };
00417 
00418 s32_t iprtetable_id = 1;
00419 struct mib_node* iprtetable_node = (struct mib_node* const)&iprteentry;
00420 struct mib_ram_array_node iprtetable = {
00421   &noleafs_get_object_def,
00422   &noleafs_get_value,
00423   &noleafs_set_test,
00424   &noleafs_set_value,
00425   MIB_NODE_RA,
00426   0,
00427   &iprtetable_id,
00428   &iprtetable_node
00429 };
00430 
00431 /** index root node for ipAddrTable */
00432 struct mib_list_rootnode ipaddrtree_root = {
00433   &noleafs_get_object_def,
00434   &noleafs_get_value,
00435   &noleafs_set_test,
00436   &noleafs_set_value,
00437   MIB_NODE_LR,
00438   0,
00439   NULL,
00440   NULL,
00441   0
00442 };
00443 const s32_t ipaddrentry_ids[5] = { 1, 2, 3, 4, 5 };
00444 struct mib_node* const ipaddrentry_nodes[5] = {
00445   (struct mib_node* const)&ipaddrtree_root,
00446   (struct mib_node* const)&ipaddrtree_root,
00447   (struct mib_node* const)&ipaddrtree_root,
00448   (struct mib_node* const)&ipaddrtree_root,
00449   (struct mib_node* const)&ipaddrtree_root
00450 };
00451 const struct mib_array_node ipaddrentry = {
00452   &noleafs_get_object_def,
00453   &noleafs_get_value,
00454   &noleafs_set_test,
00455   &noleafs_set_value,
00456   MIB_NODE_AR,
00457   5,
00458   ipaddrentry_ids,
00459   ipaddrentry_nodes
00460 };
00461 
00462 s32_t ipaddrtable_id = 1;
00463 struct mib_node* ipaddrtable_node = (struct mib_node* const)&ipaddrentry;
00464 struct mib_ram_array_node ipaddrtable = {
00465   &noleafs_get_object_def,
00466   &noleafs_get_value,
00467   &noleafs_set_test,
00468   &noleafs_set_value,
00469   MIB_NODE_RA,
00470   0,
00471   &ipaddrtable_id,
00472   &ipaddrtable_node
00473 };
00474 
00475 /* ip .1.3.6.1.2.1.4 */
00476 const mib_scalar_node ip_scalar = {
00477   &ip_get_object_def,
00478   &ip_get_value ,
00479   &ip_set_test,
00480   &noleafs_set_value,
00481   MIB_NODE_SC,
00482   0
00483 };
00484 const s32_t ip_ids[23] = { 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22, 23 };
00485 struct mib_node* const ip_nodes[23] = {
00486   (struct mib_node* const)&ip_scalar, (struct mib_node* const)&ip_scalar,
00487   (struct mib_node* const)&ip_scalar, (struct mib_node* const)&ip_scalar,
00488   (struct mib_node* const)&ip_scalar, (struct mib_node* const)&ip_scalar,
00489   (struct mib_node* const)&ip_scalar, (struct mib_node* const)&ip_scalar,
00490   (struct mib_node* const)&ip_scalar, (struct mib_node* const)&ip_scalar,
00491   (struct mib_node* const)&ip_scalar, (struct mib_node* const)&ip_scalar,
00492   (struct mib_node* const)&ip_scalar, (struct mib_node* const)&ip_scalar,
00493   (struct mib_node* const)&ip_scalar, (struct mib_node* const)&ip_scalar,
00494   (struct mib_node* const)&ip_scalar, (struct mib_node* const)&ip_scalar,
00495   (struct mib_node* const)&ip_scalar, (struct mib_node* const)&ipaddrtable,
00496   (struct mib_node* const)&iprtetable, (struct mib_node* const)&ipntomtable,
00497   (struct mib_node* const)&ip_scalar
00498 };
00499 const struct mib_array_node mib2_ip = {
00500   &noleafs_get_object_def,
00501   &noleafs_get_value,
00502   &noleafs_set_test,
00503   &noleafs_set_value,
00504   MIB_NODE_AR,
00505   23,
00506   ip_ids,
00507   ip_nodes
00508 };
00509 
00510 /** index root node for atTable */
00511 struct mib_list_rootnode arptree_root = {
00512   &noleafs_get_object_def,
00513   &noleafs_get_value,
00514   &noleafs_set_test,
00515   &noleafs_set_value,
00516   MIB_NODE_LR,
00517   0,
00518   NULL,
00519   NULL,
00520   0
00521 };
00522 const s32_t atentry_ids[3] = { 1, 2, 3 };
00523 struct mib_node* const atentry_nodes[3] = {
00524   (struct mib_node* const)&arptree_root,
00525   (struct mib_node* const)&arptree_root,
00526   (struct mib_node* const)&arptree_root
00527 };
00528 const struct mib_array_node atentry = {
00529   &noleafs_get_object_def,
00530   &noleafs_get_value,
00531   &noleafs_set_test,
00532   &noleafs_set_value,
00533   MIB_NODE_AR,
00534   3,
00535   atentry_ids,
00536   atentry_nodes
00537 };
00538 
00539 const s32_t attable_id = 1;
00540 struct mib_node* const attable_node = (struct mib_node* const)&atentry;
00541 const struct mib_array_node attable = {
00542   &noleafs_get_object_def,
00543   &noleafs_get_value,
00544   &noleafs_set_test,
00545   &noleafs_set_value,
00546   MIB_NODE_AR,
00547   1,
00548   &attable_id,
00549   &attable_node
00550 };
00551 
00552 /* at .1.3.6.1.2.1.3 */
00553 s32_t at_id = 1;
00554 struct mib_node* mib2_at_node = (struct mib_node* const)&attable;
00555 struct mib_ram_array_node at = {
00556   &noleafs_get_object_def,
00557   &noleafs_get_value,
00558   &noleafs_set_test,
00559   &noleafs_set_value,
00560   MIB_NODE_RA,
00561   0,
00562   &at_id,
00563   &mib2_at_node
00564 };
00565 
00566 /** index root node for ifTable */
00567 struct mib_list_rootnode iflist_root = {
00568   &ifentry_get_object_def,
00569   &ifentry_get_value,
00570 #if SNMP_SAFE_REQUESTS
00571   &noleafs_set_test,
00572   &noleafs_set_value,
00573 #else /* SNMP_SAFE_REQUESTS */
00574   &ifentry_set_test,
00575   &ifentry_set_value,
00576 #endif /* SNMP_SAFE_REQUESTS */
00577   MIB_NODE_LR,
00578   0,
00579   NULL,
00580   NULL,
00581   0
00582 };
00583 const s32_t ifentry_ids[22] = { 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22 };
00584 struct mib_node* const ifentry_nodes[22] = {
00585   (struct mib_node* const)&iflist_root, (struct mib_node* const)&iflist_root,
00586   (struct mib_node* const)&iflist_root, (struct mib_node* const)&iflist_root,
00587   (struct mib_node* const)&iflist_root, (struct mib_node* const)&iflist_root,
00588   (struct mib_node* const)&iflist_root, (struct mib_node* const)&iflist_root,
00589   (struct mib_node* const)&iflist_root, (struct mib_node* const)&iflist_root,
00590   (struct mib_node* const)&iflist_root, (struct mib_node* const)&iflist_root,
00591   (struct mib_node* const)&iflist_root, (struct mib_node* const)&iflist_root,
00592   (struct mib_node* const)&iflist_root, (struct mib_node* const)&iflist_root,
00593   (struct mib_node* const)&iflist_root, (struct mib_node* const)&iflist_root,
00594   (struct mib_node* const)&iflist_root, (struct mib_node* const)&iflist_root,
00595   (struct mib_node* const)&iflist_root, (struct mib_node* const)&iflist_root
00596 };
00597 const struct mib_array_node ifentry = {
00598   &noleafs_get_object_def,
00599   &noleafs_get_value,
00600   &noleafs_set_test,
00601   &noleafs_set_value,
00602   MIB_NODE_AR,
00603   22,
00604   ifentry_ids,
00605   ifentry_nodes
00606 };
00607 
00608 s32_t iftable_id = 1;
00609 struct mib_node* iftable_node = (struct mib_node* const)&ifentry;
00610 struct mib_ram_array_node iftable = {
00611   &noleafs_get_object_def,
00612   &noleafs_get_value,
00613   &noleafs_set_test,
00614   &noleafs_set_value,
00615   MIB_NODE_RA,
00616   0,
00617   &iftable_id,
00618   &iftable_node
00619 };
00620 
00621 /* interfaces .1.3.6.1.2.1.2 */
00622 const mib_scalar_node interfaces_scalar = {
00623   &interfaces_get_object_def,
00624   &interfaces_get_value,
00625   &noleafs_set_test,
00626   &noleafs_set_value,
00627   MIB_NODE_SC,
00628   0
00629 };
00630 const s32_t interfaces_ids[2] = { 1, 2 };
00631 struct mib_node* const interfaces_nodes[2] = {
00632   (struct mib_node* const)&interfaces_scalar, (struct mib_node* const)&iftable
00633 };
00634 const struct mib_array_node interfaces = {
00635   &noleafs_get_object_def,
00636   &noleafs_get_value,
00637   &noleafs_set_test,
00638   &noleafs_set_value,
00639   MIB_NODE_AR,
00640   2,
00641   interfaces_ids,
00642   interfaces_nodes
00643 };
00644 
00645 
00646 /*             0 1 2 3 4 5 6 */
00647 /* system .1.3.6.1.2.1.1 */
00648 const mib_scalar_node sys_tem_scalar = {
00649   &system_get_object_def,
00650   &system_get_value,
00651   &system_set_test,
00652   &system_set_value,
00653   MIB_NODE_SC,
00654   0
00655 };
00656 const s32_t sys_tem_ids[7] = { 1, 2, 3, 4, 5, 6, 7 };
00657 struct mib_node* const sys_tem_nodes[7] = {
00658   (struct mib_node* const)&sys_tem_scalar, (struct mib_node* const)&sys_tem_scalar,
00659   (struct mib_node* const)&sys_tem_scalar, (struct mib_node* const)&sys_tem_scalar,
00660   (struct mib_node* const)&sys_tem_scalar, (struct mib_node* const)&sys_tem_scalar,
00661   (struct mib_node* const)&sys_tem_scalar
00662 };
00663 /* work around name issue with 'sys_tem', some compiler(s?) seem to reserve 'system' */
00664 const struct mib_array_node sys_tem = {
00665   &noleafs_get_object_def,
00666   &noleafs_get_value,
00667   &noleafs_set_test,
00668   &noleafs_set_value,
00669   MIB_NODE_AR,
00670   7,
00671   sys_tem_ids,
00672   sys_tem_nodes
00673 };
00674 
00675 /* mib-2 .1.3.6.1.2.1 */
00676 #if LWIP_TCP
00677 #define MIB2_GROUPS 8
00678 #else
00679 #define MIB2_GROUPS 7
00680 #endif
00681 const s32_t mib2_ids[MIB2_GROUPS] =
00682 {
00683   1,
00684   2,
00685   3,
00686   4,
00687   5,
00688 #if LWIP_TCP
00689   6,
00690 #endif
00691   7,
00692   11
00693 };
00694 struct mib_node* const mib2_nodes[MIB2_GROUPS] = {
00695   (struct mib_node* const)&sys_tem,
00696   (struct mib_node* const)&interfaces,
00697   (struct mib_node* const)&at,
00698   (struct mib_node* const)&mib2_ip,
00699   (struct mib_node* const)&icmp,
00700 #if LWIP_TCP
00701   (struct mib_node* const)&tcp,
00702 #endif
00703   (struct mib_node* const)&udp,
00704   (struct mib_node* const)&snmp
00705 };
00706 
00707 const struct mib_array_node mib2 = {
00708   &noleafs_get_object_def,
00709   &noleafs_get_value,
00710   &noleafs_set_test,
00711   &noleafs_set_value,
00712   MIB_NODE_AR,
00713   MIB2_GROUPS,
00714   mib2_ids,
00715   mib2_nodes
00716 };
00717 
00718 /* mgmt .1.3.6.1.2 */
00719 const s32_t mgmt_ids[1] = { 1 };
00720 struct mib_node* const mgmt_nodes[1] = { (struct mib_node* const)&mib2 };
00721 const struct mib_array_node mgmt = {
00722   &noleafs_get_object_def,
00723   &noleafs_get_value,
00724   &noleafs_set_test,
00725   &noleafs_set_value,
00726   MIB_NODE_AR,
00727   1,
00728   mgmt_ids,
00729   mgmt_nodes
00730 };
00731 
00732 /* internet .1.3.6.1 */
00733 #if SNMP_PRIVATE_MIB
00734 s32_t internet_ids[2] = { 2, 4 };
00735 struct mib_node* const internet_nodes[2] = { (struct mib_node* const)&mgmt, (struct mib_node* const)&private };
00736 const struct mib_array_node internet = {
00737   &noleafs_get_object_def,
00738   &noleafs_get_value,
00739   &noleafs_set_test,
00740   &noleafs_set_value,
00741   MIB_NODE_AR,
00742   2,
00743   internet_ids,
00744   internet_nodes
00745 };
00746 #else
00747 const s32_t internet_ids[1] = { 2 };
00748 struct mib_node* const internet_nodes[1] = { (struct mib_node* const)&mgmt };
00749 const struct mib_array_node internet = {
00750   &noleafs_get_object_def,
00751   &noleafs_get_value,
00752   &noleafs_set_test,
00753   &noleafs_set_value,
00754   MIB_NODE_AR,
00755   1,
00756   internet_ids,
00757   internet_nodes
00758 };
00759 #endif
00760 
00761 /** mib-2.system.sysObjectID  */
00762 static struct snmp_obj_id sysobjid = {SNMP_SYSOBJID_LEN, SNMP_SYSOBJID};
00763 /** enterprise ID for generic TRAPs, .iso.org.dod.internet.mgmt.mib-2.snmp */
00764 static struct snmp_obj_id snmpgrp_id = {7,{1,3,6,1,2,1,11}};
00765 /** mib-2.system.sysServices */
00766 static const s32_t sysservices = SNMP_SYSSERVICES;
00767 
00768 /** mib-2.system.sysDescr */
00769 static const u8_t sysdescr_len_default = 4;
00770 static const u8_t sysdescr_default[] = "lwIP";
00771 static u8_t* sysdescr_len_ptr = (u8_t*)&sysdescr_len_default;
00772 static u8_t* sysdescr_ptr = (u8_t*)&sysdescr_default[0];
00773 /** mib-2.system.sysContact */
00774 static const u8_t syscontact_len_default = 0;
00775 static const u8_t syscontact_default[] = "";
00776 static u8_t* syscontact_len_ptr = (u8_t*)&syscontact_len_default;
00777 static u8_t* syscontact_ptr = (u8_t*)&syscontact_default[0];
00778 /** mib-2.system.sysName */
00779 static const u8_t sysname_len_default = 8;
00780 static const u8_t sysname_default[] = "FQDN-unk";
00781 static u8_t* sysname_len_ptr = (u8_t*)&sysname_len_default;
00782 static u8_t* sysname_ptr = (u8_t*)&sysname_default[0];
00783 /** mib-2.system.sysLocation */
00784 static const u8_t syslocation_len_default = 0;
00785 static const u8_t syslocation_default[] = "";
00786 static u8_t* syslocation_len_ptr = (u8_t*)&syslocation_len_default;
00787 static u8_t* syslocation_ptr = (u8_t*)&syslocation_default[0];
00788 /** mib-2.snmp.snmpEnableAuthenTraps */
00789 static const u8_t snmpenableauthentraps_default = 2; /* disabled */
00790 static u8_t* snmpenableauthentraps_ptr = (u8_t*)&snmpenableauthentraps_default;
00791 
00792 /** mib-2.interfaces.ifTable.ifEntry.ifSpecific (zeroDotZero) */
00793 static const struct snmp_obj_id ifspecific = {2, {0, 0}};
00794 /** mib-2.ip.ipRouteTable.ipRouteEntry.ipRouteInfo (zeroDotZero) */
00795 static const struct snmp_obj_id iprouteinfo = {2, {0, 0}};
00796 
00797 
00798 
00799 /* mib-2.system counter(s) */
00800 static u32_t sysuptime = 0;
00801 
00802 /* mib-2.ip counter(s) */
00803 static u32_t ipinreceives = 0,
00804              ipinhdrerrors = 0,
00805              ipinaddrerrors = 0,
00806              ipforwdatagrams = 0,
00807              ipinunknownprotos = 0,
00808              ipindiscards = 0,
00809              ipindelivers = 0,
00810              ipoutrequests = 0,
00811              ipoutdiscards = 0,
00812              ipoutnoroutes = 0,
00813              ipreasmreqds = 0,
00814              ipreasmoks = 0,
00815              ipreasmfails = 0,
00816              ipfragoks = 0,
00817              ipfragfails = 0,
00818              ipfragcreates = 0,
00819              iproutingdiscards = 0;
00820 /* mib-2.icmp counter(s) */
00821 static u32_t icmpinmsgs = 0,
00822              icmpinerrors = 0,
00823              icmpindestunreachs = 0,
00824              icmpintimeexcds = 0,
00825              icmpinparmprobs = 0,
00826              icmpinsrcquenchs = 0,
00827              icmpinredirects = 0,
00828              icmpinechos = 0,
00829              icmpinechoreps = 0,
00830              icmpintimestamps = 0,
00831              icmpintimestampreps = 0,
00832              icmpinaddrmasks = 0,
00833              icmpinaddrmaskreps = 0,
00834              icmpoutmsgs = 0,
00835              icmpouterrors = 0,
00836              icmpoutdestunreachs = 0,
00837              icmpouttimeexcds = 0,
00838              icmpoutparmprobs = 0,
00839              icmpoutsrcquenchs = 0,
00840              icmpoutredirects = 0,
00841              icmpoutechos = 0,
00842              icmpoutechoreps = 0,
00843              icmpouttimestamps = 0,
00844              icmpouttimestampreps = 0,
00845              icmpoutaddrmasks = 0,
00846              icmpoutaddrmaskreps = 0;
00847 /* mib-2.tcp counter(s) */
00848 static u32_t tcpactiveopens = 0,
00849              tcppassiveopens = 0,
00850              tcpattemptfails = 0,
00851              tcpestabresets = 0,
00852              tcpinsegs = 0,
00853              tcpoutsegs = 0,
00854              tcpretranssegs = 0,
00855              tcpinerrs = 0,
00856              tcpoutrsts = 0;
00857 /* mib-2.udp counter(s) */
00858 static u32_t udpindatagrams = 0,
00859              udpnoports = 0,
00860              udpinerrors = 0,
00861              udpoutdatagrams = 0;
00862 /* mib-2.snmp counter(s) */
00863 static u32_t snmpinpkts = 0,
00864              snmpoutpkts = 0,
00865              snmpinbadversions = 0,
00866              snmpinbadcommunitynames = 0,
00867              snmpinbadcommunityuses = 0,
00868              snmpinasnparseerrs = 0,
00869              snmpintoobigs = 0,
00870              snmpinnosuchnames = 0,
00871              snmpinbadvalues = 0,
00872              snmpinreadonlys = 0,
00873              snmpingenerrs = 0,
00874              snmpintotalreqvars = 0,
00875              snmpintotalsetvars = 0,
00876              snmpingetrequests = 0,
00877              snmpingetnexts = 0,
00878              snmpinsetrequests = 0,
00879              snmpingetresponses = 0,
00880              snmpintraps = 0,
00881              snmpouttoobigs = 0,
00882              snmpoutnosuchnames = 0,
00883              snmpoutbadvalues = 0,
00884              snmpoutgenerrs = 0,
00885              snmpoutgetrequests = 0,
00886              snmpoutgetnexts = 0,
00887              snmpoutsetrequests = 0,
00888              snmpoutgetresponses = 0,
00889              snmpouttraps = 0;
00890 
00891 
00892 
00893 /* prototypes of the following functions are in lwip/src/include/lwip/snmp.h */
00894 /**
00895  * Copy octet string.
00896  *
00897  * @param dst points to destination
00898  * @param src points to source
00899  * @param n number of octets to copy.
00900  */
00901 void ocstrncpy(u8_t *dst, u8_t *src, u8_t n)
00902 {
00903   while (n > 0)
00904   {
00905     n--;
00906     *dst++ = *src++;
00907   }
00908 }
00909 
00910 /**
00911  * Copy object identifier (s32_t) array.
00912  *
00913  * @param dst points to destination
00914  * @param src points to source
00915  * @param n number of sub identifiers to copy.
00916  */
00917 void objectidncpy(s32_t *dst, s32_t *src, u8_t n)
00918 {
00919   while(n > 0)
00920   {
00921     n--;
00922     *dst++ = *src++;
00923   }
00924 }
00925 
00926 /**
00927  * Initializes sysDescr pointers.
00928  *
00929  * @param str if non-NULL then copy str pointer
00930  * @param len points to string length, excluding zero terminator
00931  */
00932 void snmp_set_sysdesr(u8_t *str, u8_t *len)
00933 {
00934   if (str != NULL)
00935   {
00936     sysdescr_ptr = str;
00937     sysdescr_len_ptr = len;
00938   }
00939 }
00940 
00941 void snmp_get_sysobjid_ptr(struct snmp_obj_id **oid)
00942 {
00943   *oid = &sysobjid;
00944 }
00945 
00946 /**
00947  * Initializes sysObjectID value.
00948  *
00949  * @param oid points to stuct snmp_obj_id to copy
00950  */
00951 void snmp_set_sysobjid(struct snmp_obj_id *oid)
00952 {
00953   sysobjid = *oid;
00954 }
00955 
00956 /**
00957  * Must be called at regular 10 msec interval from a timer interrupt
00958  * or signal handler depending on your runtime environment.
00959  */
00960 void snmp_inc_sysuptime(void)
00961 {
00962   sysuptime++;
00963 }
00964 
00965 void snmp_add_sysuptime(u32_t value)
00966 {
00967   sysuptime+=value;
00968 }
00969 
00970 void snmp_get_sysuptime(u32_t *value)
00971 {
00972   SNMP_GET_SYSUPTIME(sysuptime);
00973   *value = sysuptime;
00974 }
00975 
00976 /**
00977  * Initializes sysContact pointers,
00978  * e.g. ptrs to non-volatile memory external to lwIP.
00979  *
00980  * @param ocstr if non-NULL then copy str pointer
00981  * @param ocstrlen points to string length, excluding zero terminator
00982  */
00983 void snmp_set_syscontact(u8_t *ocstr, u8_t *ocstrlen)
00984 {
00985   if (ocstr != NULL)
00986   {
00987     syscontact_ptr = ocstr;
00988     syscontact_len_ptr = ocstrlen;
00989   }
00990 }
00991 
00992 /**
00993  * Initializes sysName pointers,
00994  * e.g. ptrs to non-volatile memory external to lwIP.
00995  *
00996  * @param ocstr if non-NULL then copy str pointer
00997  * @param ocstrlen points to string length, excluding zero terminator
00998  */
00999 void snmp_set_sysname(u8_t *ocstr, u8_t *ocstrlen)
01000 {
01001   if (ocstr != NULL)
01002   {
01003     sysname_ptr = ocstr;
01004     sysname_len_ptr = ocstrlen;
01005   }
01006 }
01007 
01008 /**
01009  * Initializes sysLocation pointers,
01010  * e.g. ptrs to non-volatile memory external to lwIP.
01011  *
01012  * @param ocstr if non-NULL then copy str pointer
01013  * @param ocstrlen points to string length, excluding zero terminator
01014  */
01015 void snmp_set_syslocation(u8_t *ocstr, u8_t *ocstrlen)
01016 {
01017   if (ocstr != NULL)
01018   {
01019     syslocation_ptr = ocstr;
01020     syslocation_len_ptr = ocstrlen;
01021   }
01022 }
01023 
01024 
01025 void snmp_add_ifinoctets(struct netif *ni, u32_t value)
01026 {
01027   ni->ifinoctets += value;
01028 }
01029 
01030 void snmp_inc_ifinucastpkts(struct netif *ni)
01031 {
01032   (ni->ifinucastpkts)++;
01033 }
01034 
01035 void snmp_inc_ifinnucastpkts(struct netif *ni)
01036 {
01037   (ni->ifinnucastpkts)++;
01038 }
01039 
01040 void snmp_inc_ifindiscards(struct netif *ni)
01041 {
01042   (ni->ifindiscards)++;
01043 }
01044 
01045 void snmp_add_ifoutoctets(struct netif *ni, u32_t value)
01046 {
01047   ni->ifoutoctets += value;
01048 }
01049 
01050 void snmp_inc_ifoutucastpkts(struct netif *ni)
01051 {
01052   (ni->ifoutucastpkts)++;
01053 }
01054 
01055 void snmp_inc_ifoutnucastpkts(struct netif *ni)
01056 {
01057   (ni->ifoutnucastpkts)++;
01058 }
01059 
01060 void snmp_inc_ifoutdiscards(struct netif *ni)
01061 {
01062   (ni->ifoutdiscards)++;
01063 }
01064 
01065 void snmp_inc_iflist(void)
01066 {
01067   struct mib_list_node *if_node = NULL;
01068 
01069   snmp_mib_node_insert(&iflist_root, iflist_root.count + 1, &if_node);
01070   /* enable getnext traversal on filled table */
01071   iftable.maxlength = 1;
01072 }
01073 
01074 void snmp_dec_iflist(void)
01075 {
01076   snmp_mib_node_delete(&iflist_root, iflist_root.tail);
01077   /* disable getnext traversal on empty table */
01078   if(iflist_root.count == 0) iftable.maxlength = 0;
01079 }
01080 
01081 /**
01082  * Inserts ARP table indexes (.xIfIndex.xNetAddress)
01083  * into arp table index trees (both atTable and ipNetToMediaTable).
01084  */
01085 void snmp_insert_arpidx_tree(struct netif *ni, struct ip_addr *ip)
01086 {
01087   struct mib_list_rootnode *at_rn;
01088   struct mib_list_node *at_node;
01089   struct ip_addr hip;
01090   s32_t arpidx[5];
01091   u8_t level, tree;
01092 
01093   LWIP_ASSERT("ni != NULL", ni != NULL);
01094   snmp_netiftoifindex(ni, &arpidx[0]);
01095   hip.addr = ntohl(ip->addr);
01096   snmp_iptooid(&hip, &arpidx[1]);
01097 
01098   for (tree = 0; tree < 2; tree++)
01099   {
01100     if (tree == 0)
01101     {
01102       at_rn = &arptree_root;
01103     }
01104     else
01105     {
01106       at_rn = &ipntomtree_root;
01107     }
01108     for (level = 0; level < 5; level++)
01109     {
01110       at_node = NULL;
01111       snmp_mib_node_insert(at_rn, arpidx[level], &at_node);
01112       if ((level != 4) && (at_node != NULL))
01113       {
01114         if (at_node->nptr == NULL)
01115         {
01116           at_rn = snmp_mib_lrn_alloc();
01117           at_node->nptr = (struct mib_node*)at_rn;
01118           if (at_rn != NULL)
01119           {
01120             if (level == 3)
01121             {
01122               if (tree == 0)
01123               {
01124                 at_rn->get_object_def = atentry_get_object_def;
01125                 at_rn->get_value = atentry_get_value;
01126               }
01127               else
01128               {
01129                 at_rn->get_object_def = ip_ntomentry_get_object_def ;
01130                 at_rn->get_value = ip_ntomentry_get_value;
01131               }
01132               at_rn->set_test = noleafs_set_test;
01133               at_rn->set_value = noleafs_set_value;
01134             }
01135           }
01136           else
01137           {
01138             /* at_rn == NULL, malloc failure */
01139             LWIP_DEBUGF(SNMP_MIB_DEBUG,("snmp_insert_arpidx_tree() insert failed, mem full"));
01140             break;
01141           }
01142         }
01143         else
01144         {
01145           at_rn = (struct mib_list_rootnode*)at_node->nptr;
01146         }
01147       }
01148     }
01149   }
01150   /* enable getnext traversal on filled tables */
01151   at.maxlength = 1;
01152   ipntomtable.maxlength = 1;
01153 }
01154 
01155 /**
01156  * Removes ARP table indexes (.xIfIndex.xNetAddress)
01157  * from arp table index trees.
01158  */
01159 void snmp_delete_arpidx_tree(struct netif *ni, struct ip_addr *ip)
01160 {
01161   struct mib_list_rootnode *at_rn, *next, *del_rn[5];
01162   struct mib_list_node *at_n, *del_n[5];
01163   struct ip_addr hip;
01164   s32_t arpidx[5];
01165   u8_t fc, tree, level, del_cnt;
01166 
01167   snmp_netiftoifindex(ni, &arpidx[0]);
01168   hip.addr = ntohl(ip->addr);
01169   snmp_iptooid(&hip, &arpidx[1]);
01170 
01171   for (tree = 0; tree < 2; tree++)
01172   {
01173     /* mark nodes for deletion */
01174     if (tree == 0)
01175     {
01176       at_rn = &arptree_root;
01177     }
01178     else
01179     {
01180       at_rn = &ipntomtree_root;
01181     }
01182     level = 0;
01183     del_cnt = 0;
01184     while ((level < 5) && (at_rn != NULL))
01185     {
01186       fc = snmp_mib_node_find(at_rn, arpidx[level], &at_n);
01187       if (fc == 0)
01188       {
01189         /* arpidx[level] does not exist */
01190         del_cnt = 0;
01191         at_rn = NULL;
01192       }
01193       else if (fc == 1)
01194       {
01195         del_rn[del_cnt] = at_rn;
01196         del_n[del_cnt] = at_n;
01197         del_cnt++;
01198         at_rn = (struct mib_list_rootnode*)(at_n->nptr);
01199       }
01200       else if (fc == 2)
01201       {
01202         /* reset delete (2 or more childs) */
01203         del_cnt = 0;
01204         at_rn = (struct mib_list_rootnode*)(at_n->nptr);
01205       }
01206       level++;
01207     }
01208     /* delete marked index nodes */
01209     while (del_cnt > 0)
01210     {
01211       del_cnt--;
01212 
01213       at_rn = del_rn[del_cnt];
01214       at_n = del_n[del_cnt];
01215 
01216       next = snmp_mib_node_delete(at_rn, at_n);
01217       if (next != NULL)
01218       {
01219         LWIP_ASSERT("next_count == 0",next->count == 0);
01220         snmp_mib_lrn_free(next);
01221       }
01222     }
01223   }
01224   /* disable getnext traversal on empty tables */
01225   if(arptree_root.count == 0) at.maxlength = 0;
01226   if(ipntomtree_root.count == 0) ipntomtable.maxlength = 0;
01227 }
01228 
01229 void snmp_inc_ipinreceives(void)
01230 {
01231   ipinreceives++;
01232 }
01233 
01234 void snmp_inc_ipinhdrerrors(void)
01235 {
01236   ipinhdrerrors++;
01237 }
01238 
01239 void snmp_inc_ipinaddrerrors(void)
01240 {
01241   ipinaddrerrors++;
01242 }
01243 
01244 void snmp_inc_ipforwdatagrams(void)
01245 {
01246   ipforwdatagrams++;
01247 }
01248 
01249 void snmp_inc_ipinunknownprotos(void)
01250 {
01251   ipinunknownprotos++;
01252 }
01253 
01254 void snmp_inc_ipindiscards(void)
01255 {
01256   ipindiscards++;
01257 }
01258 
01259 void snmp_inc_ipindelivers(void)
01260 {
01261   ipindelivers++;
01262 }
01263 
01264 void snmp_inc_ipoutrequests(void)
01265 {
01266   ipoutrequests++;
01267 }
01268 
01269 void snmp_inc_ipoutdiscards(void)
01270 {
01271   ipoutdiscards++;
01272 }
01273 
01274 void snmp_inc_ipoutnoroutes(void)
01275 {
01276   ipoutnoroutes++;
01277 }
01278 
01279 void snmp_inc_ipreasmreqds(void)
01280 {
01281   ipreasmreqds++;
01282 }
01283 
01284 void snmp_inc_ipreasmoks(void)
01285 {
01286   ipreasmoks++;
01287 }
01288 
01289 void snmp_inc_ipreasmfails(void)
01290 {
01291   ipreasmfails++;
01292 }
01293 
01294 void snmp_inc_ipfragoks(void)
01295 {
01296   ipfragoks++;
01297 }
01298 
01299 void snmp_inc_ipfragfails(void)
01300 {
01301   ipfragfails++;
01302 }
01303 
01304 void snmp_inc_ipfragcreates(void)
01305 {
01306   ipfragcreates++;
01307 }
01308 
01309 void snmp_inc_iproutingdiscards(void)
01310 {
01311   iproutingdiscards++;
01312 }
01313 
01314 /**
01315  * Inserts ipAddrTable indexes (.ipAdEntAddr)
01316  * into index tree.
01317  */
01318 void snmp_insert_ipaddridx_tree(struct netif *ni)
01319 {
01320   struct mib_list_rootnode *ipa_rn;
01321   struct mib_list_node *ipa_node;
01322   struct ip_addr ip;
01323   s32_t ipaddridx[4];
01324   u8_t level;
01325 
01326   LWIP_ASSERT("ni != NULL", ni != NULL);
01327   ip.addr = ntohl(ni->ip_addr.addr);
01328   snmp_iptooid(&ip, &ipaddridx[0]);
01329 
01330   level = 0;
01331   ipa_rn = &ipaddrtree_root;
01332   while (level < 4)
01333   {
01334     ipa_node = NULL;
01335     snmp_mib_node_insert(ipa_rn, ipaddridx[level], &ipa_node);
01336     if ((level != 3) && (ipa_node != NULL))
01337     {
01338       if (ipa_node->nptr == NULL)
01339       {
01340         ipa_rn = snmp_mib_lrn_alloc();
01341         ipa_node->nptr = (struct mib_node*)ipa_rn;
01342         if (ipa_rn != NULL)
01343         {
01344           if (level == 2)
01345           {
01346             ipa_rn->get_object_def = ip_addrentry_get_object_def;
01347             ipa_rn->get_value = ip_addrentry_get_value ;
01348             ipa_rn->set_test = noleafs_set_test;
01349             ipa_rn->set_value = noleafs_set_value;
01350           }
01351         }
01352         else
01353         {
01354           /* ipa_rn == NULL, malloc failure */
01355           LWIP_DEBUGF(SNMP_MIB_DEBUG,("snmp_insert_ipaddridx_tree() insert failed, mem full"));
01356           break;
01357         }
01358       }
01359       else
01360       {
01361         ipa_rn = (struct mib_list_rootnode*)ipa_node->nptr;
01362       }
01363     }
01364     level++;
01365   }
01366   /* enable getnext traversal on filled table */
01367   ipaddrtable.maxlength = 1;
01368 }
01369 
01370 /**
01371  * Removes ipAddrTable indexes (.ipAdEntAddr)
01372  * from index tree.
01373  */
01374 void snmp_delete_ipaddridx_tree(struct netif *ni)
01375 {
01376   struct mib_list_rootnode *ipa_rn, *next, *del_rn[4];
01377   struct mib_list_node *ipa_n, *del_n[4];
01378   struct ip_addr ip;
01379   s32_t ipaddridx[4];
01380   u8_t fc, level, del_cnt;
01381 
01382   LWIP_ASSERT("ni != NULL", ni != NULL);
01383   ip.addr = ntohl(ni->ip_addr.addr);
01384   snmp_iptooid(&ip, &ipaddridx[0]);
01385 
01386   /* mark nodes for deletion */
01387   level = 0;
01388   del_cnt = 0;
01389   ipa_rn = &ipaddrtree_root;
01390   while ((level < 4) && (ipa_rn != NULL))
01391   {
01392     fc = snmp_mib_node_find(ipa_rn, ipaddridx[level], &ipa_n);
01393     if (fc == 0)
01394     {
01395       /* ipaddridx[level] does not exist */
01396       del_cnt = 0;
01397       ipa_rn = NULL;
01398     }
01399     else if (fc == 1)
01400     {
01401       del_rn[del_cnt] = ipa_rn;
01402       del_n[del_cnt] = ipa_n;
01403       del_cnt++;
01404       ipa_rn = (struct mib_list_rootnode*)(ipa_n->nptr);
01405     }
01406     else if (fc == 2)
01407     {
01408       /* reset delete (2 or more childs) */
01409       del_cnt = 0;
01410       ipa_rn = (struct mib_list_rootnode*)(ipa_n->nptr);
01411     }
01412     level++;
01413   }
01414   /* delete marked index nodes */
01415   while (del_cnt > 0)
01416   {
01417     del_cnt--;
01418 
01419     ipa_rn = del_rn[del_cnt];
01420     ipa_n = del_n[del_cnt];
01421 
01422     next = snmp_mib_node_delete(ipa_rn, ipa_n);
01423     if (next != NULL)
01424     {
01425       LWIP_ASSERT("next_count == 0",next->count == 0);
01426       snmp_mib_lrn_free(next);
01427     }
01428   }
01429   /* disable getnext traversal on empty table */
01430   if (ipaddrtree_root.count == 0) ipaddrtable.maxlength = 0;
01431 }
01432 
01433 /**
01434  * Inserts ipRouteTable indexes (.ipRouteDest)
01435  * into index tree.
01436  *
01437  * @param dflt non-zero for the default rte, zero for network rte
01438  * @param ni points to network interface for this rte
01439  *
01440  * @todo record sysuptime for _this_ route when it is installed
01441  *   (needed for ipRouteAge) in the netif.
01442  */
01443 void snmp_insert_iprteidx_tree(u8_t dflt, struct netif *ni)
01444 {
01445   u8_t insert = 0;
01446   struct ip_addr dst;
01447 
01448   if (dflt != 0)
01449   {
01450     /* the default route 0.0.0.0 */
01451     dst.addr = 0;
01452     insert = 1;
01453   }
01454   else
01455   {
01456     /* route to the network address */
01457     dst.addr = ntohl(ni->ip_addr.addr & ni->netmask.addr);
01458     /* exclude 0.0.0.0 network (reserved for default rte) */
01459     if (dst.addr != 0) insert = 1;
01460   }
01461   if (insert)
01462   {
01463     struct mib_list_rootnode *iprte_rn;
01464     struct mib_list_node *iprte_node;
01465     s32_t iprteidx[4];
01466     u8_t level;
01467 
01468     snmp_iptooid(&dst, &iprteidx[0]);
01469     level = 0;
01470     iprte_rn = &iprtetree_root;
01471     while (level < 4)
01472     {
01473       iprte_node = NULL;
01474       snmp_mib_node_insert(iprte_rn, iprteidx[level], &iprte_node);
01475       if ((level != 3) && (iprte_node != NULL))
01476       {
01477         if (iprte_node->nptr == NULL)
01478         {
01479           iprte_rn = snmp_mib_lrn_alloc();
01480           iprte_node->nptr = (struct mib_node*)iprte_rn;
01481           if (iprte_rn != NULL)
01482           {
01483             if (level == 2)
01484             {
01485               iprte_rn->get_object_def = ip_rteentry_get_object_def ;
01486               iprte_rn->get_value = ip_rteentry_get_value ;
01487               iprte_rn->set_test = noleafs_set_test;
01488               iprte_rn->set_value = noleafs_set_value;
01489             }
01490           }
01491           else
01492           {
01493             /* iprte_rn == NULL, malloc failure */
01494             LWIP_DEBUGF(SNMP_MIB_DEBUG,("snmp_insert_iprteidx_tree() insert failed, mem full"));
01495             break;
01496           }
01497         }
01498         else
01499         {
01500           iprte_rn = (struct mib_list_rootnode*)iprte_node->nptr;
01501         }
01502       }
01503       level++;
01504     }
01505   }
01506   /* enable getnext traversal on filled table */
01507   iprtetable.maxlength = 1;
01508 }
01509 
01510 /**
01511  * Removes ipRouteTable indexes (.ipRouteDest)
01512  * from index tree.
01513  *
01514  * @param dflt non-zero for the default rte, zero for network rte
01515  * @param ni points to network interface for this rte or NULL
01516  *   for default route to be removed.
01517  */
01518 void snmp_delete_iprteidx_tree(u8_t dflt, struct netif *ni)
01519 {
01520   u8_t delete = 0;
01521   struct ip_addr dst;
01522 
01523   if (dflt != 0)
01524   {
01525     /* the default route 0.0.0.0 */
01526     dst.addr = 0;
01527     delete = 1;
01528   }
01529   else
01530   {
01531     /* route to the network address */
01532     dst.addr = ntohl(ni->ip_addr.addr & ni->netmask.addr);
01533     /* exclude 0.0.0.0 network (reserved for default rte) */
01534     if (dst.addr != 0) delete = 1;
01535   }
01536   if (delete)
01537   {
01538     struct mib_list_rootnode *iprte_rn, *next, *del_rn[4];
01539     struct mib_list_node *iprte_n, *del_n[4];
01540     s32_t iprteidx[4];
01541     u8_t fc, level, del_cnt;
01542 
01543     snmp_iptooid(&dst, &iprteidx[0]);
01544     /* mark nodes for deletion */
01545     level = 0;
01546     del_cnt = 0;
01547     iprte_rn = &iprtetree_root;
01548     while ((level < 4) && (iprte_rn != NULL))
01549     {
01550       fc = snmp_mib_node_find(iprte_rn, iprteidx[level], &iprte_n);
01551       if (fc == 0)
01552       {
01553         /* iprteidx[level] does not exist */
01554         del_cnt = 0;
01555         iprte_rn = NULL;
01556       }
01557       else if (fc == 1)
01558       {
01559         del_rn[del_cnt] = iprte_rn;
01560         del_n[del_cnt] = iprte_n;
01561         del_cnt++;
01562         iprte_rn = (struct mib_list_rootnode*)(iprte_n->nptr);
01563       }
01564       else if (fc == 2)
01565       {
01566         /* reset delete (2 or more childs) */
01567         del_cnt = 0;
01568         iprte_rn = (struct mib_list_rootnode*)(iprte_n->nptr);
01569       }
01570       level++;
01571     }
01572     /* delete marked index nodes */
01573     while (del_cnt > 0)
01574     {
01575       del_cnt--;
01576 
01577       iprte_rn = del_rn[del_cnt];
01578       iprte_n = del_n[del_cnt];
01579 
01580       next = snmp_mib_node_delete(iprte_rn, iprte_n);
01581       if (next != NULL)
01582       {
01583         LWIP_ASSERT("next_count == 0",next->count == 0);
01584         snmp_mib_lrn_free(next);
01585       }
01586     }
01587   }
01588   /* disable getnext traversal on empty table */
01589   if (iprtetree_root.count == 0) iprtetable.maxlength = 0;
01590 }
01591 
01592 
01593 void snmp_inc_icmpinmsgs(void)
01594 {
01595   icmpinmsgs++;
01596 }
01597 
01598 void snmp_inc_icmpinerrors(void)
01599 {
01600   icmpinerrors++;
01601 }
01602 
01603 void snmp_inc_icmpindestunreachs(void)
01604 {
01605   icmpindestunreachs++;
01606 }
01607 
01608 void snmp_inc_icmpintimeexcds(void)
01609 {
01610   icmpintimeexcds++;
01611 }
01612 
01613 void snmp_inc_icmpinparmprobs(void)
01614 {
01615   icmpinparmprobs++;
01616 }
01617 
01618 void snmp_inc_icmpinsrcquenchs(void)
01619 {
01620   icmpinsrcquenchs++;
01621 }
01622 
01623 void snmp_inc_icmpinredirects(void)
01624 {
01625   icmpinredirects++;
01626 }
01627 
01628 void snmp_inc_icmpinechos(void)
01629 {
01630   icmpinechos++;
01631 }
01632 
01633 void snmp_inc_icmpinechoreps(void)
01634 {
01635   icmpinechoreps++;
01636 }
01637 
01638 void snmp_inc_icmpintimestamps(void)
01639 {
01640   icmpintimestamps++;
01641 }
01642 
01643 void snmp_inc_icmpintimestampreps(void)
01644 {
01645   icmpintimestampreps++;
01646 }
01647 
01648 void snmp_inc_icmpinaddrmasks(void)
01649 {
01650   icmpinaddrmasks++;
01651 }
01652 
01653 void snmp_inc_icmpinaddrmaskreps(void)
01654 {
01655   icmpinaddrmaskreps++;
01656 }
01657 
01658 void snmp_inc_icmpoutmsgs(void)
01659 {
01660   icmpoutmsgs++;
01661 }
01662 
01663 void snmp_inc_icmpouterrors(void)
01664 {
01665   icmpouterrors++;
01666 }
01667 
01668 void snmp_inc_icmpoutdestunreachs(void)
01669 {
01670   icmpoutdestunreachs++;
01671 }
01672 
01673 void snmp_inc_icmpouttimeexcds(void)
01674 {
01675   icmpouttimeexcds++;
01676 }
01677 
01678 void snmp_inc_icmpoutparmprobs(void)
01679 {
01680   icmpoutparmprobs++;
01681 }
01682 
01683 void snmp_inc_icmpoutsrcquenchs(void)
01684 {
01685   icmpoutsrcquenchs++;
01686 }
01687 
01688 void snmp_inc_icmpoutredirects(void)
01689 {
01690   icmpoutredirects++;
01691 }
01692 
01693 void snmp_inc_icmpoutechos(void)
01694 {
01695   icmpoutechos++;
01696 }
01697 
01698 void snmp_inc_icmpoutechoreps(void)
01699 {
01700   icmpoutechoreps++;
01701 }
01702 
01703 void snmp_inc_icmpouttimestamps(void)
01704 {
01705   icmpouttimestamps++;
01706 }
01707 
01708 void snmp_inc_icmpouttimestampreps(void)
01709 {
01710   icmpouttimestampreps++;
01711 }
01712 
01713 void snmp_inc_icmpoutaddrmasks(void)
01714 {
01715   icmpoutaddrmasks++;
01716 }
01717 
01718 void snmp_inc_icmpoutaddrmaskreps(void)
01719 {
01720   icmpoutaddrmaskreps++;
01721 }
01722 
01723 void snmp_inc_tcpactiveopens(void)
01724 {
01725   tcpactiveopens++;
01726 }
01727 
01728 void snmp_inc_tcppassiveopens(void)
01729 {
01730   tcppassiveopens++;
01731 }
01732 
01733 void snmp_inc_tcpattemptfails(void)
01734 {
01735   tcpattemptfails++;
01736 }
01737 
01738 void snmp_inc_tcpestabresets(void)
01739 {
01740   tcpestabresets++;
01741 }
01742 
01743 void snmp_inc_tcpinsegs(void)
01744 {
01745   tcpinsegs++;
01746 }
01747 
01748 void snmp_inc_tcpoutsegs(void)
01749 {
01750   tcpoutsegs++;
01751 }
01752 
01753 void snmp_inc_tcpretranssegs(void)
01754 {
01755   tcpretranssegs++;
01756 }
01757 
01758 void snmp_inc_tcpinerrs(void)
01759 {
01760   tcpinerrs++;
01761 }
01762 
01763 void snmp_inc_tcpoutrsts(void)
01764 {
01765   tcpoutrsts++;
01766 }
01767 
01768 void snmp_inc_udpindatagrams(void)
01769 {
01770   udpindatagrams++;
01771 }
01772 
01773 void snmp_inc_udpnoports(void)
01774 {
01775   udpnoports++;
01776 }
01777 
01778 void snmp_inc_udpinerrors(void)
01779 {
01780   udpinerrors++;
01781 }
01782 
01783 void snmp_inc_udpoutdatagrams(void)
01784 {
01785   udpoutdatagrams++;
01786 }
01787 
01788 /**
01789  * Inserts udpTable indexes (.udpLocalAddress.udpLocalPort)
01790  * into index tree.
01791  */
01792 void snmp_insert_udpidx_tree(struct udp_pcb *pcb)
01793 {
01794   struct mib_list_rootnode *udp_rn;
01795   struct mib_list_node *udp_node;
01796   struct ip_addr ip;
01797   s32_t udpidx[5];
01798   u8_t level;
01799 
01800   LWIP_ASSERT("pcb != NULL", pcb != NULL);
01801   ip.addr = ntohl(pcb->local_ip.addr);
01802   snmp_iptooid(&ip, &udpidx[0]);
01803   udpidx[4] = pcb->local_port;
01804 
01805   udp_rn = &udp_root;
01806   for (level = 0; level < 5; level++)
01807   {
01808     udp_node = NULL;
01809     snmp_mib_node_insert(udp_rn, udpidx[level], &udp_node);
01810     if ((level != 4) && (udp_node != NULL))
01811     {
01812       if (udp_node->nptr == NULL)
01813       {
01814         udp_rn = snmp_mib_lrn_alloc();
01815         udp_node->nptr = (struct mib_node*)udp_rn;
01816         if (udp_rn != NULL)
01817         {
01818           if (level == 3)
01819           {
01820             udp_rn->get_object_def = udpentry_get_object_def;
01821             udp_rn->get_value = udpentry_get_value;
01822             udp_rn->set_test = noleafs_set_test;
01823             udp_rn->set_value = noleafs_set_value;
01824           }
01825         }
01826         else
01827         {
01828           /* udp_rn == NULL, malloc failure */
01829           LWIP_DEBUGF(SNMP_MIB_DEBUG,("snmp_insert_udpidx_tree() insert failed, mem full"));
01830           break;
01831         }
01832       }
01833       else
01834       {
01835         udp_rn = (struct mib_list_rootnode*)udp_node->nptr;
01836       }
01837     }
01838   }
01839   udptable.maxlength = 1;
01840 }
01841 
01842 /**
01843  * Removes udpTable indexes (.udpLocalAddress.udpLocalPort)
01844  * from index tree.
01845  */
01846 void snmp_delete_udpidx_tree(struct udp_pcb *pcb)
01847 {
01848   struct mib_list_rootnode *udp_rn, *next, *del_rn[5];
01849   struct mib_list_node *udp_n, *del_n[5];
01850   struct ip_addr ip;
01851   s32_t udpidx[5];
01852   u8_t bindings, fc, level, del_cnt;
01853 
01854   LWIP_ASSERT("pcb != NULL", pcb != NULL);
01855   ip.addr = ntohl(pcb->local_ip.addr);
01856   snmp_iptooid(&ip, &udpidx[0]);
01857   udpidx[4] = pcb->local_port;
01858 
01859   /* count PCBs for a given binding
01860      (e.g. when reusing ports or for temp output PCBs) */
01861   bindings = 0;
01862   pcb = udp_pcbs;
01863   while ((pcb != NULL))
01864   {
01865     if ((pcb->local_ip.addr == ip.addr) &&
01866         (pcb->local_port == udpidx[4]))
01867     {
01868       bindings++;
01869     }
01870     pcb = pcb->next;
01871   }
01872   if (bindings == 1)
01873   {
01874     /* selectively remove */
01875     /* mark nodes for deletion */
01876     level = 0;
01877     del_cnt = 0;
01878     udp_rn = &udp_root;
01879     while ((level < 5) && (udp_rn != NULL))
01880     {
01881       fc = snmp_mib_node_find(udp_rn, udpidx[level], &udp_n);
01882       if (fc == 0)
01883       {
01884         /* udpidx[level] does not exist */
01885         del_cnt = 0;
01886         udp_rn = NULL;
01887       }
01888       else if (fc == 1)
01889       {
01890         del_rn[del_cnt] = udp_rn;
01891         del_n[del_cnt] = udp_n;
01892         del_cnt++;
01893         udp_rn = (struct mib_list_rootnode*)(udp_n->nptr);
01894       }
01895       else if (fc == 2)
01896       {
01897         /* reset delete (2 or more childs) */
01898         del_cnt = 0;
01899         udp_rn = (struct mib_list_rootnode*)(udp_n->nptr);
01900       }
01901       level++;
01902     }
01903     /* delete marked index nodes */
01904     while (del_cnt > 0)
01905     {
01906       del_cnt--;
01907 
01908       udp_rn = del_rn[del_cnt];
01909       udp_n = del_n[del_cnt];
01910 
01911       next = snmp_mib_node_delete(udp_rn, udp_n);
01912       if (next != NULL)
01913       {
01914         LWIP_ASSERT("next_count == 0",next->count == 0);
01915         snmp_mib_lrn_free(next);
01916       }
01917     }
01918   }
01919   /* disable getnext traversal on empty table */
01920   if (udp_root.count == 0) udptable.maxlength = 0;
01921 }
01922 
01923 
01924 void snmp_inc_snmpinpkts(void)
01925 {
01926   snmpinpkts++;
01927 }
01928 
01929 void snmp_inc_snmpoutpkts(void)
01930 {
01931   snmpoutpkts++;
01932 }
01933 
01934 void snmp_inc_snmpinbadversions(void)
01935 {
01936   snmpinbadversions++;
01937 }
01938 
01939 void snmp_inc_snmpinbadcommunitynames(void)
01940 {
01941   snmpinbadcommunitynames++;
01942 }
01943 
01944 void snmp_inc_snmpinbadcommunityuses(void)
01945 {
01946   snmpinbadcommunityuses++;
01947 }
01948 
01949 void snmp_inc_snmpinasnparseerrs(void)
01950 {
01951   snmpinasnparseerrs++;
01952 }
01953 
01954 void snmp_inc_snmpintoobigs(void)
01955 {
01956   snmpintoobigs++;
01957 }
01958 
01959 void snmp_inc_snmpinnosuchnames(void)
01960 {
01961   snmpinnosuchnames++;
01962 }
01963 
01964 void snmp_inc_snmpinbadvalues(void)
01965 {
01966   snmpinbadvalues++;
01967 }
01968 
01969 void snmp_inc_snmpinreadonlys(void)
01970 {
01971   snmpinreadonlys++;
01972 }
01973 
01974 void snmp_inc_snmpingenerrs(void)
01975 {
01976   snmpingenerrs++;
01977 }
01978 
01979 void snmp_add_snmpintotalreqvars(u8_t value)
01980 {
01981   snmpintotalreqvars += value;
01982 }
01983 
01984 void snmp_add_snmpintotalsetvars(u8_t value)
01985 {
01986   snmpintotalsetvars += value;
01987 }
01988 
01989 void snmp_inc_snmpingetrequests(void)
01990 {
01991   snmpingetrequests++;
01992 }
01993 
01994 void snmp_inc_snmpingetnexts(void)
01995 {
01996   snmpingetnexts++;
01997 }
01998 
01999 void snmp_inc_snmpinsetrequests(void)
02000 {
02001   snmpinsetrequests++;
02002 }
02003 
02004 void snmp_inc_snmpingetresponses(void)
02005 {
02006   snmpingetresponses++;
02007 }
02008 
02009 void snmp_inc_snmpintraps(void)
02010 {
02011   snmpintraps++;
02012 }
02013 
02014 void snmp_inc_snmpouttoobigs(void)
02015 {
02016   snmpouttoobigs++;
02017 }
02018 
02019 void snmp_inc_snmpoutnosuchnames(void)
02020 {
02021   snmpoutnosuchnames++;
02022 }
02023 
02024 void snmp_inc_snmpoutbadvalues(void)
02025 {
02026   snmpoutbadvalues++;
02027 }
02028 
02029 void snmp_inc_snmpoutgenerrs(void)
02030 {
02031   snmpoutgenerrs++;
02032 }
02033 
02034 void snmp_inc_snmpoutgetrequests(void)
02035 {
02036   snmpoutgetrequests++;
02037 }
02038 
02039 void snmp_inc_snmpoutgetnexts(void)
02040 {
02041   snmpoutgetnexts++;
02042 }
02043 
02044 void snmp_inc_snmpoutsetrequests(void)
02045 {
02046   snmpoutsetrequests++;
02047 }
02048 
02049 void snmp_inc_snmpoutgetresponses(void)
02050 {
02051   snmpoutgetresponses++;
02052 }
02053 
02054 void snmp_inc_snmpouttraps(void)
02055 {
02056   snmpouttraps++;
02057 }
02058 
02059 void snmp_get_snmpgrpid_ptr(struct snmp_obj_id **oid)
02060 {
02061   *oid = &snmpgrp_id;
02062 }
02063 
02064 void snmp_set_snmpenableauthentraps(u8_t *value)
02065 {
02066   if (value != NULL)
02067   {
02068     snmpenableauthentraps_ptr = value;
02069   }
02070 }
02071 
02072 void snmp_get_snmpenableauthentraps(u8_t *value)
02073 {
02074   *value = *snmpenableauthentraps_ptr;
02075 }
02076 
02077 void
02078 noleafs_get_object_def(u8_t ident_len, s32_t *ident, struct obj_def *od)
02079 {
02080   LWIP_UNUSED_ARG(ident_len);
02081   LWIP_UNUSED_ARG(ident);
02082   od->instance = MIB_OBJECT_NONE;
02083 }
02084 
02085 void
02086 noleafs_get_value(struct obj_def *od, u16_t len, void *value)
02087 {
02088   LWIP_UNUSED_ARG(od);
02089   LWIP_UNUSED_ARG(len);
02090   LWIP_UNUSED_ARG(value);
02091 }
02092 
02093 u8_t
02094 noleafs_set_test(struct obj_def *od, u16_t len, void *value)
02095 {
02096   LWIP_UNUSED_ARG(od);
02097   LWIP_UNUSED_ARG(len);
02098   LWIP_UNUSED_ARG(value);
02099   /* can't set */
02100   return 0;
02101 }
02102 
02103 void
02104 noleafs_set_value(struct obj_def *od, u16_t len, void *value)
02105 {
02106   LWIP_UNUSED_ARG(od);
02107   LWIP_UNUSED_ARG(len);
02108   LWIP_UNUSED_ARG(value);
02109 }
02110 
02111 
02112 /**
02113  * Returns systems object definitions.
02114  *
02115  * @param ident_len the address length (2)
02116  * @param ident points to objectname.0 (object id trailer)
02117  * @param od points to object definition.
02118  */
02119 static void
02120 system_get_object_def(u8_t ident_len, s32_t *ident, struct obj_def *od)
02121 {
02122   u8_t id;
02123 
02124   /* return to object name, adding index depth (1) */
02125   ident_len += 1;
02126   ident -= 1;
02127   if (ident_len == 2)
02128   {
02129     od->id_inst_len = ident_len;
02130     od->id_inst_ptr = ident;
02131 
02132     id = ident[0];
02133     LWIP_DEBUGF(SNMP_MIB_DEBUG,("get_object_def system.%"U16_F".0\n",(u16_t)id));
02134     switch (id)
02135     {
02136       case 1: /* sysDescr */
02137         od->instance = MIB_OBJECT_SCALAR;
02138         od->access = MIB_OBJECT_READ_ONLY;
02139         od->asn_type = (SNMP_ASN1_UNIV | SNMP_ASN1_PRIMIT | SNMP_ASN1_OC_STR);
02140         od->v_len = *sysdescr_len_ptr;
02141         break;
02142       case 2: /* sysObjectID */
02143         od->instance = MIB_OBJECT_SCALAR;
02144         od->access = MIB_OBJECT_READ_ONLY;
02145         od->asn_type = (SNMP_ASN1_UNIV | SNMP_ASN1_PRIMIT | SNMP_ASN1_OBJ_ID);
02146         od->v_len = sysobjid.len * sizeof(s32_t);
02147         break;
02148       case 3: /* sysUpTime */
02149         od->instance = MIB_OBJECT_SCALAR;
02150         od->access = MIB_OBJECT_READ_ONLY;
02151         od->asn_type = (SNMP_ASN1_APPLIC | SNMP_ASN1_PRIMIT | SNMP_ASN1_TIMETICKS);
02152         od->v_len = sizeof(u32_t);
02153         break;
02154       case 4: /* sysContact */
02155         od->instance = MIB_OBJECT_SCALAR;
02156         od->access = MIB_OBJECT_READ_WRITE;
02157         od->asn_type = (SNMP_ASN1_UNIV | SNMP_ASN1_PRIMIT | SNMP_ASN1_OC_STR);
02158         od->v_len = *syscontact_len_ptr;
02159         break;
02160       case 5: /* sysName */
02161         od->instance = MIB_OBJECT_SCALAR;
02162         od->access = MIB_OBJECT_READ_WRITE;
02163         od->asn_type = (SNMP_ASN1_UNIV | SNMP_ASN1_PRIMIT | SNMP_ASN1_OC_STR);
02164         od->v_len = *sysname_len_ptr;
02165         break;
02166       case 6: /* sysLocation */
02167         od->instance = MIB_OBJECT_SCALAR;
02168         od->access = MIB_OBJECT_READ_WRITE;
02169         od->asn_type = (SNMP_ASN1_UNIV | SNMP_ASN1_PRIMIT | SNMP_ASN1_OC_STR);
02170         od->v_len = *syslocation_len_ptr;
02171         break;
02172       case 7: /* sysServices */
02173         od->instance = MIB_OBJECT_SCALAR;
02174         od->access = MIB_OBJECT_READ_ONLY;
02175         od->asn_type = (SNMP_ASN1_UNIV | SNMP_ASN1_PRIMIT | SNMP_ASN1_INTEG);
02176         od->v_len = sizeof(s32_t);
02177         break;
02178       default:
02179         LWIP_DEBUGF(SNMP_MIB_DEBUG,("system_get_object_def: no such object\n"));
02180         od->instance = MIB_OBJECT_NONE;
02181         break;
02182     };
02183   }
02184   else
02185   {
02186     LWIP_DEBUGF(SNMP_MIB_DEBUG,("system_get_object_def: no scalar\n"));
02187     od->instance = MIB_OBJECT_NONE;
02188   }
02189 }
02190 
02191 /**
02192  * Returns system object value.
02193  *
02194  * @param ident_len the address length (2)
02195  * @param ident points to objectname.0 (object id trailer)
02196  * @param len return value space (in bytes)
02197  * @param value points to (varbind) space to copy value into.
02198  */
02199 static void
02200 system_get_value(struct obj_def *od, u16_t len, void *value)
02201 {
02202   u8_t id;
02203 
02204   id = od->id_inst_ptr[0];
02205   switch (id)
02206   {
02207     case 1: /* sysDescr */
02208       ocstrncpy(value,sysdescr_ptr, len);
02209       break;
02210     case 2: /* sysObjectID */
02211       objectidncpy((s32_t*)value, (s32_t*)sysobjid.id, (u8_t)(len / sizeof(s32_t)));
02212       break;
02213     case 3: /* sysUpTime */
02214       {
02215         snmp_get_sysuptime(value);
02216       }
02217       break;
02218     case 4: /* sysContact */
02219       ocstrncpy(value,syscontact_ptr,len);
02220       break;
02221     case 5: /* sysName */
02222       ocstrncpy(value,sysname_ptr,len);
02223       break;
02224     case 6: /* sysLocation */
02225       ocstrncpy(value,syslocation_ptr,len);
02226       break;
02227     case 7: /* sysServices */
02228       {
02229         s32_t *sint_ptr = value;
02230         *sint_ptr = sysservices;
02231       }
02232       break;
02233   };
02234 }
02235 
02236 static u8_t
02237 system_set_test(struct obj_def *od, u16_t len, void *value)
02238 {
02239   u8_t id, set_ok;
02240 
02241   LWIP_UNUSED_ARG(value);
02242   set_ok = 0;
02243   id = od->id_inst_ptr[0];
02244   switch (id)
02245   {
02246     case 4: /* sysContact */
02247       if ((syscontact_ptr != syscontact_default) &&
02248           (len <= 255))
02249       {
02250         set_ok = 1;
02251       }
02252       break;
02253     case 5: /* sysName */
02254       if ((sysname_ptr != sysname_default) &&
02255           (len <= 255))
02256       {
02257         set_ok = 1;
02258       }
02259       break;
02260     case 6: /* sysLocation */
02261       if ((syslocation_ptr != syslocation_default) &&
02262           (len <= 255))
02263       {
02264         set_ok = 1;
02265       }
02266       break;
02267   };
02268   return set_ok;
02269 }
02270 
02271 static void
02272 system_set_value(struct obj_def *od, u16_t len, void *value)
02273 {
02274   u8_t id;
02275 
02276   id = od->id_inst_ptr[0];
02277   switch (id)
02278   {
02279     case 4: /* sysContact */
02280       ocstrncpy(syscontact_ptr,value,len);
02281       *syscontact_len_ptr = len;
02282       break;
02283     case 5: /* sysName */
02284       ocstrncpy(sysname_ptr,value,len);
02285       *sysname_len_ptr = len;
02286       break;
02287     case 6: /* sysLocation */
02288       ocstrncpy(syslocation_ptr,value,len);
02289       *syslocation_len_ptr = len;
02290       break;
02291   };
02292 }
02293 
02294 /**
02295  * Returns interfaces.ifnumber object definition.
02296  *
02297  * @param ident_len the address length (2)
02298  * @param ident points to objectname.index
02299  * @param od points to object definition.
02300  */
02301 static void
02302 interfaces_get_object_def(u8_t ident_len, s32_t *ident, struct obj_def *od)
02303 {
02304   /* return to object name, adding index depth (1) */
02305   ident_len += 1;
02306   ident -= 1;
02307   if (ident_len == 2)
02308   {
02309     od->id_inst_len = ident_len;
02310     od->id_inst_ptr = ident;
02311 
02312     od->instance = MIB_OBJECT_SCALAR;
02313     od->access = MIB_OBJECT_READ_ONLY;
02314     od->asn_type = (SNMP_ASN1_UNIV | SNMP_ASN1_PRIMIT | SNMP_ASN1_INTEG);
02315     od->v_len = sizeof(s32_t);
02316   }
02317   else
02318   {
02319     LWIP_DEBUGF(SNMP_MIB_DEBUG,("interfaces_get_object_def: no scalar\n"));
02320     od->instance = MIB_OBJECT_NONE;
02321   }
02322 }
02323 
02324 /**
02325  * Returns interfaces.ifnumber object value.
02326  *
02327  * @param ident_len the address length (2)
02328  * @param ident points to objectname.0 (object id trailer)
02329  * @param len return value space (in bytes)
02330  * @param value points to (varbind) space to copy value into.
02331  */
02332 static void
02333 interfaces_get_value(struct obj_def *od, u16_t len, void *value)
02334 {
02335   LWIP_UNUSED_ARG(len);
02336   if (od->id_inst_ptr[0] == 1)
02337   {
02338     s32_t *sint_ptr = value;
02339     *sint_ptr = iflist_root.count;
02340   }
02341 }
02342 
02343 /**
02344  * Returns ifentry object definitions.
02345  *
02346  * @param ident_len the address length (2)
02347  * @param ident points to objectname.index
02348  * @param od points to object definition.
02349  */
02350 static void
02351 ifentry_get_object_def(u8_t ident_len, s32_t *ident, struct obj_def *od)
02352 {
02353   u8_t id;
02354 
02355   /* return to object name, adding index depth (1) */
02356   ident_len += 1;
02357   ident -= 1;
02358   if (ident_len == 2)
02359   {
02360     od->id_inst_len = ident_len;
02361     od->id_inst_ptr = ident;
02362 
02363     id = ident[0];
02364     LWIP_DEBUGF(SNMP_MIB_DEBUG,("get_object_def ifentry.%"U16_F"\n",(u16_t)id));
02365     switch (id)
02366     {
02367       case 1: /* ifIndex */
02368       case 3: /* ifType */
02369       case 4: /* ifMtu */
02370       case 8: /* ifOperStatus */
02371         od->instance = MIB_OBJECT_TAB;
02372         od->access = MIB_OBJECT_READ_ONLY;
02373         od->asn_type = (SNMP_ASN1_UNIV | SNMP_ASN1_PRIMIT | SNMP_ASN1_INTEG);
02374         od->v_len = sizeof(s32_t);
02375         break;
02376       case 2: /* ifDescr */
02377         od->instance = MIB_OBJECT_TAB;
02378         od->access = MIB_OBJECT_READ_ONLY;
02379         od->asn_type = (SNMP_ASN1_UNIV | SNMP_ASN1_PRIMIT | SNMP_ASN1_OC_STR);
02380         /** @todo this should be some sort of sizeof(struct netif.name) */
02381         od->v_len = 2;
02382         break;
02383       case 5: /* ifSpeed */
02384       case 21: /* ifOutQLen */
02385         od->instance = MIB_OBJECT_TAB;
02386         od->access = MIB_OBJECT_READ_ONLY;
02387         od->asn_type = (SNMP_ASN1_APPLIC | SNMP_ASN1_PRIMIT | SNMP_ASN1_GAUGE);
02388         od->v_len = sizeof(u32_t);
02389         break;
02390       case 6: /* ifPhysAddress */
02391         {
02392           struct netif *netif;
02393 
02394           snmp_ifindextonetif(ident[1], &netif);
02395           od->instance = MIB_OBJECT_TAB;
02396           od->access = MIB_OBJECT_READ_ONLY;
02397           od->asn_type = (SNMP_ASN1_UNIV | SNMP_ASN1_PRIMIT | SNMP_ASN1_OC_STR);
02398           od->v_len = netif->hwaddr_len;
02399         }
02400         break;
02401       case 7: /* ifAdminStatus */
02402         od->instance = MIB_OBJECT_TAB;
02403         od->access = MIB_OBJECT_READ_WRITE;
02404         od->asn_type = (SNMP_ASN1_UNIV | SNMP_ASN1_PRIMIT | SNMP_ASN1_INTEG);
02405         od->v_len = sizeof(s32_t);
02406         break;
02407       case 9: /* ifLastChange */
02408         od->instance = MIB_OBJECT_TAB;
02409         od->access = MIB_OBJECT_READ_ONLY;
02410         od->asn_type = (SNMP_ASN1_APPLIC | SNMP_ASN1_PRIMIT | SNMP_ASN1_TIMETICKS);
02411         od->v_len = sizeof(u32_t);
02412         break;
02413       case 10: /* ifInOctets */
02414       case 11: /* ifInUcastPkts */
02415       case 12: /* ifInNUcastPkts */
02416       case 13: /* ifInDiscarts */
02417       case 14: /* ifInErrors */
02418       case 15: /* ifInUnkownProtos */
02419       case 16: /* ifOutOctets */
02420       case 17: /* ifOutUcastPkts */
02421       case 18: /* ifOutNUcastPkts */
02422       case 19: /* ifOutDiscarts */
02423       case 20: /* ifOutErrors */
02424         od->instance = MIB_OBJECT_TAB;
02425         od->access = MIB_OBJECT_READ_ONLY;
02426         od->asn_type = (SNMP_ASN1_APPLIC | SNMP_ASN1_PRIMIT | SNMP_ASN1_COUNTER);
02427         od->v_len = sizeof(u32_t);
02428         break;
02429       case 22: /* ifSpecific */
02430         /** @note returning zeroDotZero (0.0) no media specific MIB support */
02431         od->instance = MIB_OBJECT_TAB;
02432         od->access = MIB_OBJECT_READ_ONLY;
02433         od->asn_type = (SNMP_ASN1_UNIV | SNMP_ASN1_PRIMIT | SNMP_ASN1_OBJ_ID);
02434         od->v_len = ifspecific.len * sizeof(s32_t);
02435         break;
02436       default:
02437         LWIP_DEBUGF(SNMP_MIB_DEBUG,("ifentry_get_object_def: no such object\n"));
02438         od->instance = MIB_OBJECT_NONE;
02439         break;
02440     };
02441   }
02442   else
02443   {
02444     LWIP_DEBUGF(SNMP_MIB_DEBUG,("ifentry_get_object_def: no scalar\n"));
02445     od->instance = MIB_OBJECT_NONE;
02446   }
02447 }
02448 
02449 /**
02450  * Returns ifentry object value.
02451  *
02452  * @param ident_len the address length (2)
02453  * @param ident points to objectname.0 (object id trailer)
02454  * @param len return value space (in bytes)
02455  * @param value points to (varbind) space to copy value into.
02456  */
02457 static void
02458 ifentry_get_value(struct obj_def *od, u16_t len, void *value)
02459 {
02460   struct netif *netif;
02461   u8_t id;
02462 
02463   snmp_ifindextonetif(od->id_inst_ptr[1], &netif);
02464   id = od->id_inst_ptr[0];
02465   switch (id)
02466   {
02467     case 1: /* ifIndex */
02468       {
02469         s32_t *sint_ptr = value;
02470         *sint_ptr = od->id_inst_ptr[1];
02471       }
02472       break;
02473     case 2: /* ifDescr */
02474       ocstrncpy(value,(u8_t*)netif->name,len);
02475       break;
02476     case 3: /* ifType */
02477       {
02478         s32_t *sint_ptr = value;
02479         *sint_ptr = netif->link_type;
02480       }
02481       break;
02482     case 4: /* ifMtu */
02483       {
02484         s32_t *sint_ptr = value;
02485         *sint_ptr = netif->mtu;
02486       }
02487       break;
02488     case 5: /* ifSpeed */
02489       {
02490         u32_t *uint_ptr = value;
02491         *uint_ptr = netif->link_speed;
02492       }
02493       break;
02494     case 6: /* ifPhysAddress */
02495       ocstrncpy(value,netif->hwaddr,len);
02496       break;
02497     case 7: /* ifAdminStatus */
02498 #if LWIP_NETIF_LINK_CALLBACK
02499       {
02500         s32_t *sint_ptr = value;
02501         if (netif_is_up(netif))
02502         {
02503           if (netif_is_link_up(netif))
02504           {
02505             *sint_ptr = 1; /* up */
02506           }
02507           else
02508           {
02509             *sint_ptr = 7; /* lowerLayerDown */
02510           }
02511         }
02512         else
02513         {
02514           *sint_ptr = 2; /* down */
02515         }
02516       }
02517       break;
02518 #endif
02519     case 8: /* ifOperStatus */
02520       {
02521         s32_t *sint_ptr = value;
02522         if (netif_is_up(netif))
02523         {
02524           *sint_ptr = 1;
02525         }
02526         else
02527         {
02528           *sint_ptr = 2;
02529         }
02530       }
02531       break;
02532     case 9: /* ifLastChange */
02533       {
02534         u32_t *uint_ptr = value;
02535         *uint_ptr = netif->ts;
02536       }
02537       break;
02538     case 10: /* ifInOctets */
02539       {
02540         u32_t *uint_ptr = value;
02541         *uint_ptr = netif->ifinoctets;
02542       }
02543       break;
02544     case 11: /* ifInUcastPkts */
02545       {
02546         u32_t *uint_ptr = value;
02547         *uint_ptr = netif->ifinucastpkts;
02548       }
02549       break;
02550     case 12: /* ifInNUcastPkts */
02551       {
02552         u32_t *uint_ptr = value;
02553         *uint_ptr = netif->ifinnucastpkts;
02554       }
02555       break;
02556     case 13: /* ifInDiscarts */
02557       {
02558         u32_t *uint_ptr = value;
02559         *uint_ptr = netif->ifindiscards;
02560       }
02561       break;
02562     case 14: /* ifInErrors */
02563     case 15: /* ifInUnkownProtos */
02564       /** @todo add these counters! */
02565       {
02566         u32_t *uint_ptr = value;
02567         *uint_ptr = 0;
02568       }
02569       break;
02570     case 16: /* ifOutOctets */
02571       {
02572         u32_t *uint_ptr = value;
02573         *uint_ptr = netif->ifoutoctets;
02574       }
02575       break;
02576     case 17: /* ifOutUcastPkts */
02577       {
02578         u32_t *uint_ptr = value;
02579         *uint_ptr = netif->ifoutucastpkts;
02580       }
02581       break;
02582     case 18: /* ifOutNUcastPkts */
02583       {
02584         u32_t *uint_ptr = value;
02585         *uint_ptr = netif->ifoutnucastpkts;
02586       }
02587       break;
02588     case 19: /* ifOutDiscarts */
02589       {
02590         u32_t *uint_ptr = value;
02591         *uint_ptr = netif->ifoutdiscards;
02592       }
02593       break;
02594     case 20: /* ifOutErrors */
02595        /** @todo add this counter! */
02596       {
02597         u32_t *uint_ptr = value;
02598         *uint_ptr = 0;
02599       }
02600       break;
02601     case 21: /* ifOutQLen */
02602       /** @todo figure out if this must be 0 (no queue) or 1? */
02603       {
02604         u32_t *uint_ptr = value;
02605         *uint_ptr = 0;
02606       }
02607       break;
02608     case 22: /* ifSpecific */
02609       objectidncpy((s32_t*)value, (s32_t*)ifspecific.id, (u8_t)(len / sizeof(s32_t)));
02610       break;
02611   };
02612 }
02613 
02614 #if !SNMP_SAFE_REQUESTS
02615 static u8_t
02616 ifentry_set_test (struct obj_def *od, u16_t len, void *value)
02617 {
02618   struct netif *netif;
02619   u8_t id, set_ok;
02620 
02621   set_ok = 0;
02622   snmp_ifindextonetif(od->id_inst_ptr[1], &netif);
02623   id = od->id_inst_ptr[0];
02624   switch (id)
02625   {
02626     case 7: /* ifAdminStatus */
02627       {
02628         s32_t *sint_ptr = value;
02629         if (*sint_ptr == 1 || *sint_ptr == 2)
02630           set_ok = 1;
02631       }
02632       break;
02633   }
02634   return set_ok;
02635 }
02636 
02637 static void
02638 ifentry_set_value (struct obj_def *od, u16_t len, void *value)
02639 {
02640   struct netif *netif;
02641   u8_t id;
02642 
02643   snmp_ifindextonetif(od->id_inst_ptr[1], &netif);
02644   id = od->id_inst_ptr[0];
02645   switch (id)
02646   {
02647     case 7: /* ifAdminStatus */
02648       {
02649         s32_t *sint_ptr = value;
02650         if (*sint_ptr == 1)
02651         {
02652           netif_set_up(netif);
02653         }
02654         else if (*sint_ptr == 2)
02655         {
02656           netif_set_down(netif);
02657          }
02658       }
02659       break;
02660   }
02661 }
02662 #endif /* SNMP_SAFE_REQUESTS */
02663 
02664 /**
02665  * Returns atentry object definitions.
02666  *
02667  * @param ident_len the address length (6)
02668  * @param ident points to objectname.atifindex.atnetaddress
02669  * @param od points to object definition.
02670  */
02671 static void
02672 atentry_get_object_def(u8_t ident_len, s32_t *ident, struct obj_def *od)
02673 {
02674   /* return to object name, adding index depth (5) */
02675   ident_len += 5;
02676   ident -= 5;
02677 
02678   if (ident_len == 6)
02679   {
02680     od->id_inst_len = ident_len;
02681     od->id_inst_ptr = ident;
02682 
02683     switch (ident[0])
02684     {
02685       case 1: /* atIfIndex */
02686         od->instance = MIB_OBJECT_TAB;
02687         od->access = MIB_OBJECT_READ_WRITE;
02688         od->asn_type = (SNMP_ASN1_UNIV | SNMP_ASN1_PRIMIT | SNMP_ASN1_INTEG);
02689         od->v_len = sizeof(s32_t);
02690         break;
02691       case 2: /* atPhysAddress */
02692         od->instance = MIB_OBJECT_TAB;
02693         od->access = MIB_OBJECT_READ_WRITE;
02694         od->asn_type = (SNMP_ASN1_UNIV | SNMP_ASN1_PRIMIT | SNMP_ASN1_OC_STR);
02695         od->v_len = 6; /** @todo try to use netif::hwaddr_len */
02696         break;
02697       case 3: /* atNetAddress */
02698         od->instance = MIB_OBJECT_TAB;
02699         od->access = MIB_OBJECT_READ_WRITE;
02700         od->asn_type = (SNMP_ASN1_APPLIC | SNMP_ASN1_PRIMIT | SNMP_ASN1_IPADDR);
02701         od->v_len = 4;
02702         break;
02703       default:
02704         LWIP_DEBUGF(SNMP_MIB_DEBUG,("atentry_get_object_def: no such object\n"));
02705         od->instance = MIB_OBJECT_NONE;
02706         break;
02707     }
02708   }
02709   else
02710   {
02711     LWIP_DEBUGF(SNMP_MIB_DEBUG,("atentry_get_object_def: no scalar\n"));
02712     od->instance = MIB_OBJECT_NONE;
02713   }
02714 }
02715 
02716 static void
02717 atentry_get_value(struct obj_def *od, u16_t len, void *value)
02718 {
02719 #if LWIP_ARP
02720   u8_t id;
02721   struct eth_addr* ethaddr_ret;
02722   struct ip_addr* ipaddr_ret;
02723 #endif /* LWIP_ARP */
02724   struct ip_addr ip;
02725   struct netif *netif;
02726 
02727   LWIP_UNUSED_ARG(len);
02728   LWIP_UNUSED_ARG(value);/* if !LWIP_ARP */
02729 
02730   snmp_ifindextonetif(od->id_inst_ptr[1], &netif);
02731   snmp_oidtoip(&od->id_inst_ptr[2], &ip);
02732   ip.addr = htonl(ip.addr);
02733 
02734 #if LWIP_ARP /** @todo implement a netif_find_addr */
02735   if (etharp_find_addr(netif, &ip, &ethaddr_ret, &ipaddr_ret) > -1)
02736   {
02737     id = od->id_inst_ptr[0];
02738     switch (id)
02739     {
02740       case 1: /* atIfIndex */
02741         {
02742           s32_t *sint_ptr = value;
02743           *sint_ptr = od->id_inst_ptr[1];
02744         }
02745         break;
02746       case 2: /* atPhysAddress */
02747         {
02748           struct eth_addr *dst = value;
02749 
02750           *dst = *ethaddr_ret;
02751         }
02752         break;
02753       case 3: /* atNetAddress */
02754         {
02755           struct ip_addr *dst = value;
02756 
02757           *dst = *ipaddr_ret;
02758         }
02759         break;
02760     }
02761   }
02762 #endif /* LWIP_ARP */
02763 }
02764 
02765 static void
02766 ip_get_object_def(u8_t ident_len, s32_t *ident, struct obj_def *od)
02767 {
02768   u8_t id;
02769 
02770   /* return to object name, adding index depth (1) */
02771   ident_len += 1;
02772   ident -= 1;
02773   if (ident_len == 2)
02774   {
02775     od->id_inst_len = ident_len;
02776     od->id_inst_ptr = ident;
02777 
02778     id = ident[0];
02779     LWIP_DEBUGF(SNMP_MIB_DEBUG,("get_object_def ip.%"U16_F".0\n",(u16_t)id));
02780     switch (id)
02781     {
02782       case 1: /* ipForwarding */
02783       case 2: /* ipDefaultTTL */
02784         od->instance = MIB_OBJECT_SCALAR;
02785         od->access = MIB_OBJECT_READ_WRITE;
02786         od->asn_type = (SNMP_ASN1_UNIV | SNMP_ASN1_PRIMIT | SNMP_ASN1_INTEG);
02787         od->v_len = sizeof(s32_t);
02788         break;
02789       case 3: /* ipInReceives */
02790       case 4: /* ipInHdrErrors */
02791       case 5: /* ipInAddrErrors */
02792       case 6: /* ipForwDatagrams */
02793       case 7: /* ipInUnknownProtos */
02794       case 8: /* ipInDiscards */
02795       case 9: /* ipInDelivers */
02796       case 10: /* ipOutRequests */
02797       case 11: /* ipOutDiscards */
02798       case 12: /* ipOutNoRoutes */
02799       case 14: /* ipReasmReqds */
02800       case 15: /* ipReasmOKs */
02801       case 16: /* ipReasmFails */
02802       case 17: /* ipFragOKs */
02803       case 18: /* ipFragFails */
02804       case 19: /* ipFragCreates */
02805       case 23: /* ipRoutingDiscards */
02806         od->instance = MIB_OBJECT_SCALAR;
02807         od->access = MIB_OBJECT_READ_ONLY;
02808         od->asn_type = (SNMP_ASN1_APPLIC | SNMP_ASN1_PRIMIT | SNMP_ASN1_COUNTER);
02809         od->v_len = sizeof(u32_t);
02810         break;
02811       case 13: /* ipReasmTimeout */
02812         od->instance = MIB_OBJECT_SCALAR;
02813         od->access = MIB_OBJECT_READ_ONLY;
02814         od->asn_type = (SNMP_ASN1_UNIV | SNMP_ASN1_PRIMIT | SNMP_ASN1_INTEG);
02815         od->v_len = sizeof(s32_t);
02816         break;
02817       default:
02818         LWIP_DEBUGF(SNMP_MIB_DEBUG,("ip_get_object_def: no such object\n"));
02819         od->instance = MIB_OBJECT_NONE;
02820         break;
02821     };
02822   }
02823   else
02824   {
02825     LWIP_DEBUGF(SNMP_MIB_DEBUG,("ip_get_object_def: no scalar\n"));
02826     od->instance = MIB_OBJECT_NONE;
02827   }
02828 }
02829 
02830 static void
02831 ip_get_value (struct obj_def *od, u16_t len, void *value)
02832 {
02833   u8_t id;
02834 
02835   LWIP_UNUSED_ARG(len);
02836   id = od->id_inst_ptr[0];
02837   switch (id)
02838   {
02839     case 1: /* ipForwarding */
02840       {
02841         s32_t *sint_ptr = value;
02842 #if IP_FORWARD
02843         /* forwarding */
02844         *sint_ptr = 1;
02845 #else
02846         /* not-forwarding */
02847         *sint_ptr = 2;
02848 #endif
02849       }
02850       break;
02851     case 2: /* ipDefaultTTL */
02852       {
02853         s32_t *sint_ptr = value;
02854         *sint_ptr = IP_DEFAULT_TTL;
02855       }
02856       break;
02857     case 3: /* ipInReceives */
02858       {
02859         u32_t *uint_ptr = value;
02860         *uint_ptr = ipinreceives;
02861       }
02862       break;
02863     case 4: /* ipInHdrErrors */
02864       {
02865         u32_t *uint_ptr = value;
02866         *uint_ptr = ipinhdrerrors;
02867       }
02868       break;
02869     case 5: /* ipInAddrErrors */
02870       {
02871         u32_t *uint_ptr = value;
02872         *uint_ptr = ipinaddrerrors;
02873       }
02874       break;
02875     case 6: /* ipForwDatagrams */
02876       {
02877         u32_t *uint_ptr = value;
02878         *uint_ptr = ipforwdatagrams;
02879       }
02880       break;
02881     case 7: /* ipInUnknownProtos */
02882       {
02883         u32_t *uint_ptr = value;
02884         *uint_ptr = ipinunknownprotos;
02885       }
02886       break;
02887     case 8: /* ipInDiscards */
02888       {
02889         u32_t *uint_ptr = value;
02890         *uint_ptr = ipindiscards;
02891       }
02892       break;
02893     case 9: /* ipInDelivers */
02894       {
02895         u32_t *uint_ptr = value;
02896         *uint_ptr = ipindelivers;
02897       }
02898       break;
02899     case 10: /* ipOutRequests */
02900       {
02901         u32_t *uint_ptr = value;
02902         *uint_ptr = ipoutrequests;
02903       }
02904       break;
02905     case 11: /* ipOutDiscards */
02906       {
02907         u32_t *uint_ptr = value;
02908         *uint_ptr = ipoutdiscards;
02909       }
02910       break;
02911     case 12: /* ipOutNoRoutes */
02912       {
02913         u32_t *uint_ptr = value;
02914         *uint_ptr = ipoutnoroutes;
02915       }
02916       break;
02917     case 13: /* ipReasmTimeout */
02918       {
02919         s32_t *sint_ptr = value;
02920 #if IP_REASSEMBLY
02921         *sint_ptr = IP_REASS_MAXAGE;
02922 #else
02923         *sint_ptr = 0;
02924 #endif
02925       }
02926       break;
02927     case 14: /* ipReasmReqds */
02928       {
02929         u32_t *uint_ptr = value;
02930         *uint_ptr = ipreasmreqds;
02931       }
02932       break;
02933     case 15: /* ipReasmOKs */
02934       {
02935         u32_t *uint_ptr = value;
02936         *uint_ptr = ipreasmoks;
02937       }
02938       break;
02939     case 16: /* ipReasmFails */
02940       {
02941         u32_t *uint_ptr = value;
02942         *uint_ptr = ipreasmfails;
02943       }
02944       break;
02945     case 17: /* ipFragOKs */
02946       {
02947         u32_t *uint_ptr = value;
02948         *uint_ptr = ipfragoks;
02949       }
02950       break;
02951     case 18: /* ipFragFails */
02952       {
02953         u32_t *uint_ptr = value;
02954         *uint_ptr = ipfragfails;
02955       }
02956       break;
02957     case 19: /* ipFragCreates */
02958       {
02959         u32_t *uint_ptr = value;
02960         *uint_ptr = ipfragcreates;
02961       }
02962       break;
02963     case 23: /* ipRoutingDiscards */
02964       /** @todo can lwIP discard routes at all?? hardwire this to 0?? */
02965       {
02966         u32_t *uint_ptr = value;
02967         *uint_ptr = iproutingdiscards;
02968       }
02969       break;
02970   };
02971 }
02972 
02973 /**
02974  * Test ip object value before setting.
02975  *
02976  * @param od is the object definition
02977  * @param len return value space (in bytes)
02978  * @param value points to (varbind) space to copy value from.
02979  *
02980  * @note we allow set if the value matches the hardwired value,
02981  *   otherwise return badvalue.
02982  */
02983 static u8_t
02984 ip_set_test(struct obj_def *od, u16_t len, void *value)
02985 {
02986   u8_t id, set_ok;
02987   s32_t *sint_ptr = value;
02988 
02989   LWIP_UNUSED_ARG(len);
02990   set_ok = 0;
02991   id = od->id_inst_ptr[0];
02992   switch (id)
02993   {
02994     case 1: /* ipForwarding */
02995 #if IP_FORWARD
02996       /* forwarding */
02997       if (*sint_ptr == 1)
02998 #else
02999       /* not-forwarding */
03000       if (*sint_ptr == 2)
03001 #endif
03002       {
03003         set_ok = 1;
03004       }
03005       break;
03006     case 2: /* ipDefaultTTL */
03007       if (*sint_ptr == IP_DEFAULT_TTL)
03008       {
03009         set_ok = 1;
03010       }
03011       break;
03012   };
03013   return set_ok;
03014 }
03015 
03016 static void
03017 ip_addrentry_get_object_def(u8_t ident_len, s32_t *ident, struct obj_def *od)
03018 {
03019   /* return to object name, adding index depth (4) */
03020   ident_len += 4;
03021   ident -= 4;
03022 
03023   if (ident_len == 5)
03024   {
03025     u8_t id;
03026 
03027     od->id_inst_len = ident_len;
03028     od->id_inst_ptr = ident;
03029 
03030     id = ident[0];
03031     switch (id)
03032     {
03033       case 1: /* ipAdEntAddr */
03034       case 3: /* ipAdEntNetMask */
03035         od->instance = MIB_OBJECT_TAB;
03036         od->access = MIB_OBJECT_READ_ONLY;
03037         od->asn_type = (SNMP_ASN1_APPLIC | SNMP_ASN1_PRIMIT | SNMP_ASN1_IPADDR);
03038         od->v_len = 4;
03039         break;
03040       case 2: /* ipAdEntIfIndex */
03041       case 4: /* ipAdEntBcastAddr */
03042       case 5: /* ipAdEntReasmMaxSize */
03043         od->instance = MIB_OBJECT_TAB;
03044         od->access = MIB_OBJECT_READ_ONLY;
03045         od->asn_type = (SNMP_ASN1_UNIV | SNMP_ASN1_PRIMIT | SNMP_ASN1_INTEG);
03046         od->v_len = sizeof(s32_t);
03047         break;
03048       default:
03049         LWIP_DEBUGF(SNMP_MIB_DEBUG,("ip_addrentry_get_object_def: no such object\n"));
03050         od->instance = MIB_OBJECT_NONE;
03051         break;
03052     }
03053   }
03054   else
03055   {
03056     LWIP_DEBUGF(SNMP_MIB_DEBUG,("ip_addrentry_get_object_def: no scalar\n"));
03057     od->instance = MIB_OBJECT_NONE;
03058   }
03059 }
03060 
03061 static void
03062 ip_addrentry_get_value (struct obj_def *od, u16_t len, void *value)
03063 {
03064   u8_t id;
03065   u16_t ifidx;
03066   struct ip_addr ip;
03067   struct netif *netif = netif_list;
03068 
03069   LWIP_UNUSED_ARG(len);
03070   snmp_oidtoip(&od->id_inst_ptr[1], &ip);
03071   ip.addr = htonl(ip.addr);
03072   ifidx = 0;
03073   while ((netif != NULL) && !ip_addr_cmp(&ip, &netif->ip_addr))
03074   {
03075     netif = netif->next;
03076     ifidx++;
03077   }
03078 
03079   if (netif != NULL)
03080   {
03081     id = od->id_inst_ptr[0];
03082     switch (id)
03083     {
03084       case 1: /* ipAdEntAddr */
03085         {
03086           struct ip_addr *dst = value;
03087           *dst = netif->ip_addr;
03088         }
03089         break;
03090       case 2: /* ipAdEntIfIndex */
03091         {
03092           s32_t *sint_ptr = value;
03093           *sint_ptr = ifidx + 1;
03094         }
03095         break;
03096       case 3: /* ipAdEntNetMask */
03097         {
03098           struct ip_addr *dst = value;
03099           *dst = netif->netmask;
03100         }
03101         break;
03102       case 4: /* ipAdEntBcastAddr */
03103         {
03104           s32_t *sint_ptr = value;
03105 
03106           /* lwIP oddity, there's no broadcast
03107             address in the netif we can rely on */
03108           *sint_ptr = ip_addr_broadcast.addr & 1;
03109         }
03110         break;
03111       case 5: /* ipAdEntReasmMaxSize */
03112         {
03113           s32_t *sint_ptr = value;
03114 #if IP_REASSEMBLY
03115           /* @todo The theoretical maximum is IP_REASS_MAX_PBUFS * size of the pbufs,
03116            * but only if receiving one fragmented packet at a time.
03117            * The current solution is to calculate for 2 simultaneous packets...
03118            */
03119           *sint_ptr = (IP_HLEN + ((IP_REASS_MAX_PBUFS/2) *
03120             (PBUF_POOL_BUFSIZE - PBUF_LINK_HLEN - IP_HLEN)));
03121 #else
03122           /** @todo returning MTU would be a bad thing and
03123              returning a wild guess like '576' isn't good either */
03124           *sint_ptr = 0;
03125 #endif
03126         }
03127         break;
03128     }
03129   }
03130 }
03131 
03132 /**
03133  * @note
03134  * lwIP IP routing is currently using the network addresses in netif_list.
03135  * if no suitable network IP is found in netif_list, the default_netif is used.
03136  */
03137 static void
03138 ip_rteentry_get_object_def (u8_t ident_len, s32_t *ident, struct obj_def *od)
03139 {
03140   u8_t id;
03141 
03142   /* return to object name, adding index depth (4) */
03143   ident_len += 4;
03144   ident -= 4;
03145 
03146   if (ident_len == 5)
03147   {
03148     od->id_inst_len = ident_len;
03149     od->id_inst_ptr = ident;
03150 
03151     id = ident[0];
03152     switch (id)
03153     {
03154       case 1: /* ipRouteDest */
03155       case 7: /* ipRouteNextHop */
03156       case 11: /* ipRouteMask */
03157         od->instance = MIB_OBJECT_TAB;
03158         od->access = MIB_OBJECT_READ_WRITE;
03159         od->asn_type = (SNMP_ASN1_APPLIC | SNMP_ASN1_PRIMIT | SNMP_ASN1_IPADDR);
03160         od->v_len = 4;
03161         break;
03162       case 2: /* ipRouteIfIndex */
03163       case 3: /* ipRouteMetric1 */
03164       case 4: /* ipRouteMetric2 */
03165       case 5: /* ipRouteMetric3 */
03166       case 6: /* ipRouteMetric4 */
03167       case 8: /* ipRouteType */
03168       case 10: /* ipRouteAge */
03169       case 12: /* ipRouteMetric5 */
03170         od->instance = MIB_OBJECT_TAB;
03171         od->access = MIB_OBJECT_READ_WRITE;
03172         od->asn_type = (SNMP_ASN1_UNIV | SNMP_ASN1_PRIMIT | SNMP_ASN1_INTEG);
03173         od->v_len = sizeof(s32_t);
03174         break;
03175       case 9: /* ipRouteProto */
03176         od->instance = MIB_OBJECT_TAB;
03177         od->access = MIB_OBJECT_READ_ONLY;
03178         od->asn_type = (SNMP_ASN1_UNIV | SNMP_ASN1_PRIMIT | SNMP_ASN1_INTEG);
03179         od->v_len = sizeof(s32_t);
03180         break;
03181       case 13: /* ipRouteInfo */
03182         /** @note returning zeroDotZero (0.0) no routing protocol specific MIB */
03183         od->instance = MIB_OBJECT_TAB;
03184         od->access = MIB_OBJECT_READ_ONLY;
03185         od->asn_type = (SNMP_ASN1_UNIV | SNMP_ASN1_PRIMIT | SNMP_ASN1_OBJ_ID);
03186         od->v_len = iprouteinfo.len * sizeof(s32_t);
03187         break;
03188       default:
03189         LWIP_DEBUGF(SNMP_MIB_DEBUG,("ip_rteentry_get_object_def: no such object\n"));
03190         od->instance = MIB_OBJECT_NONE;
03191         break;
03192     }
03193   }
03194   else
03195   {
03196     LWIP_DEBUGF(SNMP_MIB_DEBUG,("ip_rteentry_get_object_def: no scalar\n"));
03197     od->instance = MIB_OBJECT_NONE;
03198   }
03199 }
03200 
03201 static void
03202 ip_rteentry_get_value (struct obj_def *od, u16_t len, void *value)
03203 {
03204   struct netif *netif;
03205   struct ip_addr dest;
03206   s32_t *ident;
03207   u8_t id;
03208 
03209   ident = od->id_inst_ptr;
03210   snmp_oidtoip(&ident[1], &dest);
03211   dest.addr = htonl(dest.addr);
03212 
03213   if (dest.addr == 0)
03214   {
03215     /* ip_route() uses default netif for default route */
03216     netif = netif_default;
03217   }
03218   else
03219   {
03220     /* not using ip_route(), need exact match! */
03221     netif = netif_list;
03222     while ((netif != NULL) &&
03223             !ip_addr_netcmp(&dest, &(netif->ip_addr), &(netif->netmask)) )
03224     {
03225       netif = netif->next;
03226     }
03227   }
03228   if (netif != NULL)
03229   {
03230     id = ident[0];
03231     switch (id)
03232     {
03233       case 1: /* ipRouteDest */
03234         {
03235           struct ip_addr *dst = value;
03236 
03237           if (dest.addr == 0)
03238           {
03239             /* default rte has 0.0.0.0 dest */
03240             dst->addr = 0;
03241           }
03242           else
03243           {
03244             /* netifs have netaddress dest */
03245             dst->addr = netif->ip_addr.addr & netif->netmask.addr;
03246           }
03247         }
03248         break;
03249       case 2: /* ipRouteIfIndex */
03250         {
03251           s32_t *sint_ptr = value;
03252 
03253           snmp_netiftoifindex(netif, sint_ptr);
03254         }
03255         break;
03256       case 3: /* ipRouteMetric1 */
03257         {
03258           s32_t *sint_ptr = value;
03259 
03260           if (dest.addr == 0)
03261           {
03262             /* default rte has metric 1 */
03263             *sint_ptr = 1;
03264           }
03265           else
03266           {
03267             /* other rtes have metric 0 */
03268             *sint_ptr = 0;
03269           }
03270         }
03271         break;
03272       case 4: /* ipRouteMetric2 */
03273       case 5: /* ipRouteMetric3 */
03274       case 6: /* ipRouteMetric4 */
03275       case 12: /* ipRouteMetric5 */
03276         {
03277           s32_t *sint_ptr = value;
03278           /* not used */
03279           *sint_ptr = -1;
03280         }
03281         break;
03282       case 7: /* ipRouteNextHop */
03283         {
03284           struct ip_addr *dst = value;
03285 
03286           if (dest.addr == 0)
03287           {
03288             /* default rte: gateway */
03289             *dst = netif->gw;
03290           }
03291           else
03292           {
03293             /* other rtes: netif ip_addr  */
03294             *dst = netif->ip_addr;
03295           }
03296         }
03297         break;
03298       case 8: /* ipRouteType */
03299         {
03300           s32_t *sint_ptr = value;
03301 
03302           if (dest.addr == 0)
03303           {
03304             /* default rte is indirect */
03305             *sint_ptr = 4;
03306           }
03307           else
03308           {
03309             /* other rtes are direct */
03310             *sint_ptr = 3;
03311           }
03312         }
03313         break;
03314       case 9: /* ipRouteProto */
03315         {
03316           s32_t *sint_ptr = value;
03317           /* locally defined routes */
03318           *sint_ptr = 2;
03319         }
03320         break;
03321       case 10: /* ipRouteAge */
03322         {
03323           s32_t *sint_ptr = value;
03324           /** @todo (sysuptime - timestamp last change) / 100
03325               @see snmp_insert_iprteidx_tree() */
03326           *sint_ptr = 0;
03327         }
03328         break;
03329       case 11: /* ipRouteMask */
03330         {
03331           struct ip_addr *dst = value;
03332 
03333           if (dest.addr == 0)
03334           {
03335             /* default rte use 0.0.0.0 mask */
03336             dst->addr = 0;
03337           }
03338           else
03339           {
03340             /* other rtes use netmask */
03341             *dst = netif->netmask;
03342           }
03343         }
03344         break;
03345       case 13: /* ipRouteInfo */
03346         objectidncpy((s32_t*)value, (s32_t*)iprouteinfo.id, (u8_t)(len / sizeof(s32_t)));
03347         break;
03348     }
03349   }
03350 }
03351 
03352 static void
03353 ip_ntomentry_get_object_def (u8_t ident_len, s32_t *ident, struct obj_def *od)
03354 {
03355   /* return to object name, adding index depth (5) */
03356   ident_len += 5;
03357   ident -= 5;
03358 
03359   if (ident_len == 6)
03360   {
03361     u8_t id;
03362 
03363     od->id_inst_len = ident_len;
03364     od->id_inst_ptr = ident;
03365 
03366     id = ident[0];
03367     switch (id)
03368     {
03369       case 1: /* ipNetToMediaIfIndex */
03370       case 4: /* ipNetToMediaType */
03371         od->instance = MIB_OBJECT_TAB;
03372         od->access = MIB_OBJECT_READ_WRITE;
03373         od->asn_type = (SNMP_ASN1_UNIV | SNMP_ASN1_PRIMIT | SNMP_ASN1_INTEG);
03374         od->v_len = sizeof(s32_t);
03375         break;
03376       case 2: /* ipNetToMediaPhysAddress */
03377         od->instance = MIB_OBJECT_TAB;
03378         od->access = MIB_OBJECT_READ_WRITE;
03379         od->asn_type = (SNMP_ASN1_UNIV | SNMP_ASN1_PRIMIT | SNMP_ASN1_OC_STR);
03380         od->v_len = 6; /** @todo try to use netif::hwaddr_len */
03381         break;
03382       case 3: /* ipNetToMediaNetAddress */
03383         od->instance = MIB_OBJECT_TAB;
03384         od->access = MIB_OBJECT_READ_WRITE;
03385         od->asn_type = (SNMP_ASN1_APPLIC | SNMP_ASN1_PRIMIT | SNMP_ASN1_IPADDR);
03386         od->v_len = 4;
03387         break;
03388       default:
03389         LWIP_DEBUGF(SNMP_MIB_DEBUG,("ip_ntomentry_get_object_def: no such object\n"));
03390         od->instance = MIB_OBJECT_NONE;
03391         break;
03392     }
03393   }
03394   else
03395   {
03396     LWIP_DEBUGF(SNMP_MIB_DEBUG,("ip_ntomentry_get_object_def: no scalar\n"));
03397     od->instance = MIB_OBJECT_NONE;
03398   }
03399 }
03400 
03401 static void
03402 ip_ntomentry_get_value(struct obj_def *od, u16_t len, void *value)
03403 {
03404 #if LWIP_ARP
03405   u8_t id;
03406   struct eth_addr* ethaddr_ret;
03407   struct ip_addr* ipaddr_ret;
03408 #endif /* LWIP_ARP */
03409   struct ip_addr ip;
03410   struct netif *netif;
03411 
03412   LWIP_UNUSED_ARG(len);
03413   LWIP_UNUSED_ARG(value);/* if !LWIP_ARP */
03414 
03415   snmp_ifindextonetif(od->id_inst_ptr[1], &netif);
03416   snmp_oidtoip(&od->id_inst_ptr[2], &ip);
03417   ip.addr = htonl(ip.addr);
03418 
03419 #if LWIP_ARP /** @todo implement a netif_find_addr */
03420   if (etharp_find_addr(netif, &ip, &ethaddr_ret, &ipaddr_ret) > -1)
03421   {
03422     id = od->id_inst_ptr[0];
03423     switch (id)
03424     {
03425       case 1: /* ipNetToMediaIfIndex */
03426         {
03427           s32_t *sint_ptr = value;
03428           *sint_ptr = od->id_inst_ptr[1];
03429         }
03430         break;
03431       case 2: /* ipNetToMediaPhysAddress */
03432         {
03433           struct eth_addr *dst = value;
03434 
03435           *dst = *ethaddr_ret;
03436         }
03437         break;
03438       case 3: /* ipNetToMediaNetAddress */
03439         {
03440           struct ip_addr *dst = value;
03441 
03442           *dst = *ipaddr_ret;
03443         }
03444         break;
03445       case 4: /* ipNetToMediaType */
03446         {
03447           s32_t *sint_ptr = value;
03448           /* dynamic (?) */
03449           *sint_ptr = 3;
03450         }
03451         break;
03452     }
03453   }
03454 #endif /* LWIP_ARP */
03455 }
03456 
03457 static void
03458 icmp_get_object_def(u8_t ident_len, s32_t *ident, struct obj_def *od)
03459 {
03460   /* return to object name, adding index depth (1) */
03461   ident_len += 1;
03462   ident -= 1;
03463   if ((ident_len == 2) &&
03464       (ident[0] > 0) && (ident[0] < 27))
03465   {
03466     od->id_inst_len = ident_len;
03467     od->id_inst_ptr = ident;
03468 
03469     od->instance = MIB_OBJECT_SCALAR;
03470     od->access = MIB_OBJECT_READ_ONLY;
03471     od->asn_type = (SNMP_ASN1_APPLIC | SNMP_ASN1_PRIMIT | SNMP_ASN1_COUNTER);
03472     od->v_len = sizeof(u32_t);
03473   }
03474   else
03475   {
03476     LWIP_DEBUGF(SNMP_MIB_DEBUG,("icmp_get_object_def: no scalar\n"));
03477     od->instance = MIB_OBJECT_NONE;
03478   }
03479 }
03480 
03481 static void
03482 icmp_get_value(struct obj_def *od, u16_t len, void *value)
03483 {
03484   u32_t *uint_ptr = value;
03485   u8_t id;
03486 
03487   LWIP_UNUSED_ARG(len);
03488   id = od->id_inst_ptr[0];
03489   switch (id)
03490   {
03491     case 1: /* icmpInMsgs */
03492       *uint_ptr = icmpinmsgs;
03493       break;
03494     case 2: /* icmpInErrors */
03495       *uint_ptr = icmpinerrors;
03496       break;
03497     case 3: /* icmpInDestUnreachs */
03498       *uint_ptr = icmpindestunreachs;
03499       break;
03500     case 4: /* icmpInTimeExcds */
03501       *uint_ptr = icmpintimeexcds;
03502       break;
03503     case 5: /* icmpInParmProbs */
03504       *uint_ptr = icmpinparmprobs;
03505       break;
03506     case 6: /* icmpInSrcQuenchs */
03507       *uint_ptr = icmpinsrcquenchs;
03508       break;
03509     case 7: /* icmpInRedirects */
03510       *uint_ptr = icmpinredirects;
03511       break;
03512     case 8: /* icmpInEchos */
03513       *uint_ptr = icmpinechos;
03514       break;
03515     case 9: /* icmpInEchoReps */
03516       *uint_ptr = icmpinechoreps;
03517       break;
03518     case 10: /* icmpInTimestamps */
03519       *uint_ptr = icmpintimestamps;
03520       break;
03521     case 11: /* icmpInTimestampReps */
03522       *uint_ptr = icmpintimestampreps;
03523       break;
03524     case 12: /* icmpInAddrMasks */
03525       *uint_ptr = icmpinaddrmasks;
03526       break;
03527     case 13: /* icmpInAddrMaskReps */
03528       *uint_ptr = icmpinaddrmaskreps;
03529       break;
03530     case 14: /* icmpOutMsgs */
03531       *uint_ptr = icmpoutmsgs;
03532       break;
03533     case 15: /* icmpOutErrors */
03534       *uint_ptr = icmpouterrors;
03535       break;
03536     case 16: /* icmpOutDestUnreachs */
03537       *uint_ptr = icmpoutdestunreachs;
03538       break;
03539     case 17: /* icmpOutTimeExcds */
03540       *uint_ptr = icmpouttimeexcds;
03541       break;
03542     case 18: /* icmpOutParmProbs */
03543       *uint_ptr = icmpoutparmprobs;
03544       break;
03545     case 19: /* icmpOutSrcQuenchs */
03546       *uint_ptr = icmpoutsrcquenchs;
03547       break;
03548     case 20: /* icmpOutRedirects */
03549       *uint_ptr = icmpoutredirects;
03550       break;
03551     case 21: /* icmpOutEchos */
03552       *uint_ptr = icmpoutechos;
03553       break;
03554     case 22: /* icmpOutEchoReps */
03555       *uint_ptr = icmpoutechoreps;
03556       break;
03557     case 23: /* icmpOutTimestamps */
03558       *uint_ptr = icmpouttimestamps;
03559       break;
03560     case 24: /* icmpOutTimestampReps */
03561       *uint_ptr = icmpouttimestampreps;
03562       break;
03563     case 25: /* icmpOutAddrMasks */
03564       *uint_ptr = icmpoutaddrmasks;
03565       break;
03566     case 26: /* icmpOutAddrMaskReps */
03567       *uint_ptr = icmpoutaddrmaskreps;
03568       break;
03569   }
03570 }
03571 
03572 #if LWIP_TCP
03573 /** @todo tcp grp */
03574 static void
03575 tcp_get_object_def (u8_t ident_len, s32_t *ident, struct obj_def *od)
03576 {
03577   u8_t id;
03578 
03579   /* return to object name, adding index depth (1) */
03580   ident_len += 1;
03581   ident -= 1;
03582   if (ident_len == 2)
03583   {
03584     od->id_inst_len = ident_len;
03585     od->id_inst_ptr = ident;
03586 
03587     id = ident[0];
03588     LWIP_DEBUGF(SNMP_MIB_DEBUG,("get_object_def tcp.%"U16_F".0\n",(u16_t)id));
03589 
03590     switch (id)
03591     {
03592       case 1: /* tcpRtoAlgorithm */
03593       case 2: /* tcpRtoMin */
03594       case 3: /* tcpRtoMax */
03595       case 4: /* tcpMaxConn */
03596         od->instance = MIB_OBJECT_SCALAR;
03597         od->access = MIB_OBJECT_READ_ONLY;
03598         od->asn_type = (SNMP_ASN1_UNIV | SNMP_ASN1_PRIMIT | SNMP_ASN1_INTEG);
03599         od->v_len = sizeof(s32_t);
03600         break;
03601       case 5: /* tcpActiveOpens */
03602       case 6: /* tcpPassiveOpens */
03603       case 7: /* tcpAttemptFails */
03604       case 8: /* tcpEstabResets */
03605       case 10: /* tcpInSegs */
03606       case 11: /* tcpOutSegs */
03607       case 12: /* tcpRetransSegs */
03608       case 14: /* tcpInErrs */
03609       case 15: /* tcpOutRsts */
03610         od->instance = MIB_OBJECT_SCALAR;
03611         od->access = MIB_OBJECT_READ_ONLY;
03612         od->asn_type = (SNMP_ASN1_APPLIC | SNMP_ASN1_PRIMIT | SNMP_ASN1_COUNTER);
03613         od->v_len = sizeof(u32_t);
03614         break;
03615       case 9: /* tcpCurrEstab */
03616         od->instance = MIB_OBJECT_TAB;
03617         od->access = MIB_OBJECT_READ_ONLY;
03618         od->asn_type = (SNMP_ASN1_APPLIC | SNMP_ASN1_PRIMIT | SNMP_ASN1_GAUGE);
03619         od->v_len = sizeof(u32_t);
03620         break;
03621       default:
03622         LWIP_DEBUGF(SNMP_MIB_DEBUG,("tcp_get_object_def: no such object\n"));
03623         od->instance = MIB_OBJECT_NONE;
03624         break;
03625     };
03626   }
03627   else
03628   {
03629     LWIP_DEBUGF(SNMP_MIB_DEBUG,("tcp_get_object_def: no scalar\n"));
03630     od->instance = MIB_OBJECT_NONE;
03631   }
03632 }
03633 
03634 static void
03635 tcp_get_value(struct obj_def *od, u16_t len, void *value)
03636 {
03637   u32_t *uint_ptr = value;
03638   s32_t *sint_ptr = value;
03639   u8_t id;
03640 
03641   LWIP_UNUSED_ARG(len);
03642   id = od->id_inst_ptr[0];
03643   switch (id)
03644   {
03645     case 1: /* tcpRtoAlgorithm, vanj(4) */
03646       *sint_ptr = 4;
03647       break;
03648     case 2: /* tcpRtoMin */
03649       /* @todo not the actual value, a guess,
03650           needs to be calculated */
03651       *sint_ptr = 1000;
03652       break;
03653     case 3: /* tcpRtoMax */
03654       /* @todo not the actual value, a guess,
03655          needs to be calculated */
03656       *sint_ptr = 60000;
03657       break;
03658     case 4: /* tcpMaxConn */
03659       *sint_ptr = MEMP_NUM_TCP_PCB;
03660       break;
03661     case 5: /* tcpActiveOpens */
03662       *uint_ptr = tcpactiveopens;
03663       break;
03664     case 6: /* tcpPassiveOpens */
03665       *uint_ptr = tcppassiveopens;
03666       break;
03667     case 7: /* tcpAttemptFails */
03668       *uint_ptr = tcpattemptfails;
03669       break;
03670     case 8: /* tcpEstabResets */
03671       *uint_ptr = tcpestabresets;
03672       break;
03673     case 9: /* tcpCurrEstab */
03674       {
03675         u16_t tcpcurrestab = 0;
03676         struct tcp_pcb *pcb = tcp_active_pcbs;
03677         while (pcb != NULL)
03678         {
03679           if ((pcb->state == ESTABLISHED) ||
03680               (pcb->state == CLOSE_WAIT))
03681           {
03682             tcpcurrestab++;
03683           }
03684           pcb = pcb->next;
03685         }
03686         *uint_ptr = tcpcurrestab;
03687       }
03688       break;
03689     case 10: /* tcpInSegs */
03690       *uint_ptr = tcpinsegs;
03691       break;
03692     case 11: /* tcpOutSegs */
03693       *uint_ptr = tcpoutsegs;
03694       break;
03695     case 12: /* tcpRetransSegs */
03696       *uint_ptr = tcpretranssegs;
03697       break;
03698     case 14: /* tcpInErrs */
03699       *uint_ptr = tcpinerrs;
03700       break;
03701     case 15: /* tcpOutRsts */
03702       *uint_ptr = tcpoutrsts;
03703       break;
03704   }
03705 }
03706 #ifdef THIS_SEEMS_UNUSED
03707 static void
03708 tcpconnentry_get_object_def(u8_t ident_len, s32_t *ident, struct obj_def *od)
03709 {
03710   /* return to object name, adding index depth (10) */
03711   ident_len += 10;
03712   ident -= 10;
03713 
03714   if (ident_len == 11)
03715   {
03716     u8_t id;
03717 
03718     od->id_inst_len = ident_len;
03719     od->id_inst_ptr = ident;
03720 
03721     id = ident[0];
03722     LWIP_DEBUGF(SNMP_MIB_DEBUG,("get_object_def tcp.%"U16_F".0\n",(u16_t)id));
03723 
03724     switch (id)
03725     {
03726       case 1: /* tcpConnState */
03727         od->instance = MIB_OBJECT_TAB;
03728         od->access = MIB_OBJECT_READ_WRITE;
03729         od->asn_type = (SNMP_ASN1_UNIV | SNMP_ASN1_PRIMIT | SNMP_ASN1_INTEG);
03730         od->v_len = sizeof(s32_t);
03731         break;
03732       case 2: /* tcpConnLocalAddress */
03733       case 4: /* tcpConnRemAddress */
03734         od->instance = MIB_OBJECT_TAB;
03735         od->access = MIB_OBJECT_READ_ONLY;
03736         od->asn_type = (SNMP_ASN1_APPLIC | SNMP_ASN1_PRIMIT | SNMP_ASN1_IPADDR);
03737         od->v_len = 4;
03738         break;
03739       case 3: /* tcpConnLocalPort */
03740       case 5: /* tcpConnRemPort */
03741         od->instance = MIB_OBJECT_TAB;
03742         od->access = MIB_OBJECT_READ_ONLY;
03743         od->asn_type = (SNMP_ASN1_UNIV | SNMP_ASN1_PRIMIT | SNMP_ASN1_INTEG);
03744         od->v_len = sizeof(s32_t);
03745         break;
03746       default:
03747         LWIP_DEBUGF(SNMP_MIB_DEBUG,("tcpconnentry_get_object_def: no such object\n"));
03748         od->instance = MIB_OBJECT_NONE;
03749         break;
03750     };
03751   }
03752   else
03753   {
03754     LWIP_DEBUGF(SNMP_MIB_DEBUG,("tcpconnentry_get_object_def: no such object\n"));
03755     od->instance = MIB_OBJECT_NONE;
03756   }
03757 }
03758 
03759 static void
03760 tcpconnentry_get_value (struct obj_def *od, u16_t len, void *value)
03761 {
03762   struct ip_addr lip, rip;
03763   u16_t lport, rport;
03764   s32_t *ident;
03765 
03766   ident = od->id_inst_ptr;
03767   snmp_oidtoip(&ident[1], &lip);
03768   lip.addr = htonl(lip.addr);
03769   lport = ident[5];
03770   snmp_oidtoip(&ident[6], &rip);
03771   rip.addr = htonl(rip.addr);
03772   rport = ident[10];
03773 
03774   /** @todo find matching PCB */
03775 }
03776 #endif /* if 0 */
03777 #endif
03778 
03779 static void
03780 udp_get_object_def(u8_t ident_len, s32_t *ident, struct obj_def *od)
03781 {
03782   /* return to object name, adding index depth (1) */
03783   ident_len += 1;
03784   ident -= 1;
03785   if ((ident_len == 2) &&
03786       (ident[0] > 0) && (ident[0] < 6))
03787   {
03788     od->id_inst_len = ident_len;
03789     od->id_inst_ptr = ident;
03790 
03791     od->instance = MIB_OBJECT_SCALAR;
03792     od->access = MIB_OBJECT_READ_ONLY;
03793     od->asn_type = (SNMP_ASN1_APPLIC | SNMP_ASN1_PRIMIT | SNMP_ASN1_COUNTER);
03794     od->v_len = sizeof(u32_t);
03795   }
03796   else
03797   {
03798     LWIP_DEBUGF(SNMP_MIB_DEBUG,("udp_get_object_def: no scalar\n"));
03799     od->instance = MIB_OBJECT_NONE;
03800   }
03801 }
03802 
03803 static void
03804 udp_get_value(struct obj_def *od, u16_t len, void *value)
03805 {
03806   u32_t *uint_ptr = value;
03807   u8_t id;
03808 
03809   LWIP_UNUSED_ARG(len);
03810   id = od->id_inst_ptr[0];
03811   switch (id)
03812   {
03813     case 1: /* udpInDatagrams */
03814       *uint_ptr = udpindatagrams;
03815       break;
03816     case 2: /* udpNoPorts */
03817       *uint_ptr = udpnoports;
03818       break;
03819     case 3: /* udpInErrors */
03820       *uint_ptr = udpinerrors;
03821       break;
03822     case 4: /* udpOutDatagrams */
03823       *uint_ptr = udpoutdatagrams;
03824       break;
03825   }
03826 }
03827 
03828 static void
03829 udpentry_get_object_def(u8_t ident_len, s32_t *ident, struct obj_def *od)
03830 {
03831   /* return to object name, adding index depth (5) */
03832   ident_len += 5;
03833   ident -= 5;
03834 
03835   if (ident_len == 6)
03836   {
03837     od->id_inst_len = ident_len;
03838     od->id_inst_ptr = ident;
03839 
03840     switch (ident[0])
03841     {
03842       case 1: /* udpLocalAddress */
03843         od->instance = MIB_OBJECT_TAB;
03844         od->access = MIB_OBJECT_READ_ONLY;
03845         od->asn_type = (SNMP_ASN1_APPLIC | SNMP_ASN1_PRIMIT | SNMP_ASN1_IPADDR);
03846         od->v_len = 4;
03847         break;
03848       case 2: /* udpLocalPort */
03849         od->instance = MIB_OBJECT_TAB;
03850         od->access = MIB_OBJECT_READ_ONLY;
03851         od->asn_type = (SNMP_ASN1_UNIV | SNMP_ASN1_PRIMIT | SNMP_ASN1_INTEG);
03852         od->v_len = sizeof(s32_t);
03853         break;
03854       default:
03855         LWIP_DEBUGF(SNMP_MIB_DEBUG,("udpentry_get_object_def: no such object\n"));
03856         od->instance = MIB_OBJECT_NONE;
03857         break;
03858     }
03859   }
03860   else
03861   {
03862     LWIP_DEBUGF(SNMP_MIB_DEBUG,("udpentry_get_object_def: no scalar\n"));
03863     od->instance = MIB_OBJECT_NONE;
03864   }
03865 }
03866 
03867 static void
03868 udpentry_get_value(struct obj_def *od, u16_t len, void *value)
03869 {
03870   u8_t id;
03871   struct udp_pcb *pcb;
03872   struct ip_addr ip;
03873   u16_t port;
03874 
03875   LWIP_UNUSED_ARG(len);
03876   snmp_oidtoip(&od->id_inst_ptr[1], &ip);
03877   ip.addr = htonl(ip.addr);
03878   port = od->id_inst_ptr[5];
03879 
03880   pcb = udp_pcbs;
03881   while ((pcb != NULL) &&
03882          !((pcb->local_ip.addr == ip.addr) &&
03883            (pcb->local_port == port)))
03884   {
03885     pcb = pcb->next;
03886   }
03887 
03888   if (pcb != NULL)
03889   {
03890     id = od->id_inst_ptr[0];
03891     switch (id)
03892     {
03893       case 1: /* udpLocalAddress */
03894         {
03895           struct ip_addr *dst = value;
03896           *dst = pcb->local_ip;
03897         }
03898         break;
03899       case 2: /* udpLocalPort */
03900         {
03901           s32_t *sint_ptr = value;
03902           *sint_ptr = pcb->local_port;
03903         }
03904         break;
03905     }
03906   }
03907 }
03908 
03909 static void
03910 snmp_get_object_def(u8_t ident_len, s32_t *ident, struct obj_def *od)
03911 {
03912   /* return to object name, adding index depth (1) */
03913   ident_len += 1;
03914   ident -= 1;
03915   if (ident_len == 2)
03916   {
03917     u8_t id;
03918 
03919     od->id_inst_len = ident_len;
03920     od->id_inst_ptr = ident;
03921 
03922     id = ident[0];
03923     switch (id)
03924     {
03925       case 1: /* snmpInPkts */
03926       case 2: /* snmpOutPkts */
03927       case 3: /* snmpInBadVersions */
03928       case 4: /* snmpInBadCommunityNames */
03929       case 5: /* snmpInBadCommunityUses */
03930       case 6: /* snmpInASNParseErrs */
03931       case 8: /* snmpInTooBigs */
03932       case 9: /* snmpInNoSuchNames */
03933       case 10: /* snmpInBadValues */
03934       case 11: /* snmpInReadOnlys */
03935       case 12: /* snmpInGenErrs */
03936       case 13: /* snmpInTotalReqVars */
03937       case 14: /* snmpInTotalSetVars */
03938       case 15: /* snmpInGetRequests */
03939       case 16: /* snmpInGetNexts */
03940       case 17: /* snmpInSetRequests */
03941       case 18: /* snmpInGetResponses */
03942       case 19: /* snmpInTraps */
03943       case 20: /* snmpOutTooBigs */
03944       case 21: /* snmpOutNoSuchNames */
03945       case 22: /* snmpOutBadValues */
03946       case 24: /* snmpOutGenErrs */
03947       case 25: /* snmpOutGetRequests */
03948       case 26: /* snmpOutGetNexts */
03949       case 27: /* snmpOutSetRequests */
03950       case 28: /* snmpOutGetResponses */
03951       case 29: /* snmpOutTraps */
03952         od->instance = MIB_OBJECT_SCALAR;
03953         od->access = MIB_OBJECT_READ_ONLY;
03954         od->asn_type = (SNMP_ASN1_APPLIC | SNMP_ASN1_PRIMIT | SNMP_ASN1_COUNTER);
03955         od->v_len = sizeof(u32_t);
03956         break;
03957       case 30: /* snmpEnableAuthenTraps */
03958         od->instance = MIB_OBJECT_SCALAR;
03959         od->access = MIB_OBJECT_READ_WRITE;
03960         od->asn_type = (SNMP_ASN1_UNIV | SNMP_ASN1_PRIMIT | SNMP_ASN1_INTEG);
03961         od->v_len = sizeof(s32_t);
03962         break;
03963       default:
03964         LWIP_DEBUGF(SNMP_MIB_DEBUG,("snmp_get_object_def: no such object\n"));
03965         od->instance = MIB_OBJECT_NONE;
03966         break;
03967     };
03968   }
03969   else
03970   {
03971     LWIP_DEBUGF(SNMP_MIB_DEBUG,("snmp_get_object_def: no scalar\n"));
03972     od->instance = MIB_OBJECT_NONE;
03973   }
03974 }
03975 
03976 static void
03977 snmp_get_value(struct obj_def *od, u16_t len, void *value)
03978 {
03979   u32_t *uint_ptr = value;
03980   u8_t id;
03981 
03982   LWIP_UNUSED_ARG(len);
03983   id = od->id_inst_ptr[0];
03984   switch (id)
03985   {
03986       case 1: /* snmpInPkts */
03987         *uint_ptr = snmpinpkts;
03988         break;
03989       case 2: /* snmpOutPkts */
03990         *uint_ptr = snmpoutpkts;
03991         break;
03992       case 3: /* snmpInBadVersions */
03993         *uint_ptr = snmpinbadversions;
03994         break;
03995       case 4: /* snmpInBadCommunityNames */
03996         *uint_ptr = snmpinbadcommunitynames;
03997         break;
03998       case 5: /* snmpInBadCommunityUses */
03999         *uint_ptr = snmpinbadcommunityuses;
04000         break;
04001       case 6: /* snmpInASNParseErrs */
04002         *uint_ptr = snmpinasnparseerrs;
04003         break;
04004       case 8: /* snmpInTooBigs */
04005         *uint_ptr = snmpintoobigs;
04006         break;
04007       case 9: /* snmpInNoSuchNames */
04008         *uint_ptr = snmpinnosuchnames;
04009         break;
04010       case 10: /* snmpInBadValues */
04011         *uint_ptr = snmpinbadvalues;
04012         break;
04013       case 11: /* snmpInReadOnlys */
04014         *uint_ptr = snmpinreadonlys;
04015         break;
04016       case 12: /* snmpInGenErrs */
04017         *uint_ptr = snmpingenerrs;
04018         break;
04019       case 13: /* snmpInTotalReqVars */
04020         *uint_ptr = snmpintotalreqvars;
04021         break;
04022       case 14: /* snmpInTotalSetVars */
04023         *uint_ptr = snmpintotalsetvars;
04024         break;
04025       case 15: /* snmpInGetRequests */
04026         *uint_ptr = snmpingetrequests;
04027         break;
04028       case 16: /* snmpInGetNexts */
04029         *uint_ptr = snmpingetnexts;
04030         break;
04031       case 17: /* snmpInSetRequests */
04032         *uint_ptr = snmpinsetrequests;
04033         break;
04034       case 18: /* snmpInGetResponses */
04035         *uint_ptr = snmpingetresponses;
04036         break;
04037       case 19: /* snmpInTraps */
04038         *uint_ptr = snmpintraps;
04039         break;
04040       case 20: /* snmpOutTooBigs */
04041         *uint_ptr = snmpouttoobigs;
04042         break;
04043       case 21: /* snmpOutNoSuchNames */
04044         *uint_ptr = snmpoutnosuchnames;
04045         break;
04046       case 22: /* snmpOutBadValues */
04047         *uint_ptr = snmpoutbadvalues;
04048         break;
04049       case 24: /* snmpOutGenErrs */
04050         *uint_ptr = snmpoutgenerrs;
04051         break;
04052       case 25: /* snmpOutGetRequests */
04053         *uint_ptr = snmpoutgetrequests;
04054         break;
04055       case 26: /* snmpOutGetNexts */
04056         *uint_ptr = snmpoutgetnexts;
04057         break;
04058       case 27: /* snmpOutSetRequests */
04059         *uint_ptr = snmpoutsetrequests;
04060         break;
04061       case 28: /* snmpOutGetResponses */
04062         *uint_ptr = snmpoutgetresponses;
04063         break;
04064       case 29: /* snmpOutTraps */
04065         *uint_ptr = snmpouttraps;
04066         break;
04067       case 30: /* snmpEnableAuthenTraps */
04068         *uint_ptr = *snmpenableauthentraps_ptr;
04069         break;
04070   };
04071 }
04072 
04073 /**
04074  * Test snmp object value before setting.
04075  *
04076  * @param od is the object definition
04077  * @param len return value space (in bytes)
04078  * @param value points to (varbind) space to copy value from.
04079  */
04080 static u8_t
04081 snmp_set_test(struct obj_def *od, u16_t len, void *value)
04082 {
04083   u8_t id, set_ok;
04084 
04085   LWIP_UNUSED_ARG(len);
04086   set_ok = 0;
04087   id = od->id_inst_ptr[0];
04088   if (id == 30)
04089   {
04090     /* snmpEnableAuthenTraps */
04091     s32_t *sint_ptr = value;
04092 
04093     if (snmpenableauthentraps_ptr != &snmpenableauthentraps_default)
04094     {
04095       /* we should have writable non-volatile mem here */
04096       if ((*sint_ptr == 1) || (*sint_ptr == 2))
04097       {
04098         set_ok = 1;
04099       }
04100     }
04101     else
04102     {
04103       /* const or hardwired value */
04104       if (*sint_ptr == snmpenableauthentraps_default)
04105       {
04106         set_ok = 1;
04107       }
04108     }
04109   }
04110   return set_ok;
04111 }
04112 
04113 static void
04114 snmp_set_value(struct obj_def *od, u16_t len, void *value)
04115 {
04116   u8_t id;
04117 
04118   LWIP_UNUSED_ARG(len);
04119   id = od->id_inst_ptr[0];
04120   if (id == 30)
04121   {
04122     /* snmpEnableAuthenTraps */
04123     s32_t *sint_ptr = value;
04124     *snmpenableauthentraps_ptr = *sint_ptr;
04125   }
04126 }
04127 
04128 #endif /* LWIP_SNMP */