First getnext succes, values are returned insead of NULLs, empty tables are skipped. Limitation: a single varbind per request, so 'snmptable' will fail.

This commit is contained in:
christiaans 2006-09-06 10:14:07 +00:00
parent 56c5fdbeaf
commit 41ff80e5d3
4 changed files with 432 additions and 210 deletions

View File

@ -4,8 +4,6 @@
*
* @note the object identifiers for this MIB-2 and private MIB tree
* must be kept in sorted ascending order. This to ensure correct getnext operation.
*
* @todo optimize htonl, ntohl.
*/
/*
@ -105,17 +103,35 @@ static void snmp_get_value(struct obj_def *od, u16_t len, void *value);
/* snmp .1.3.6.1.2.1.11 */
const mib_scalar_node snmp_scalar = {
&snmp_get_object_def,
&snmp_get_value,
MIB_NODE_SC,
0
};
const s32_t snmp_ids[28] = {
1, 2, 3, 4, 5, 6, 8, 9, 10, 11, 12, 13, 14, 15, 16,
17, 18, 19, 20, 21, 22, 24, 25, 26, 27, 28, 29, 30
};
struct mib_node* const snmp_nodes[28] = {
NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL,
NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL
(struct mib_node* const)&snmp_scalar, (struct mib_node* const)&snmp_scalar,
(struct mib_node* const)&snmp_scalar, (struct mib_node* const)&snmp_scalar,
(struct mib_node* const)&snmp_scalar, (struct mib_node* const)&snmp_scalar,
(struct mib_node* const)&snmp_scalar, (struct mib_node* const)&snmp_scalar,
(struct mib_node* const)&snmp_scalar, (struct mib_node* const)&snmp_scalar,
(struct mib_node* const)&snmp_scalar, (struct mib_node* const)&snmp_scalar,
(struct mib_node* const)&snmp_scalar, (struct mib_node* const)&snmp_scalar,
(struct mib_node* const)&snmp_scalar, (struct mib_node* const)&snmp_scalar,
(struct mib_node* const)&snmp_scalar, (struct mib_node* const)&snmp_scalar,
(struct mib_node* const)&snmp_scalar, (struct mib_node* const)&snmp_scalar,
(struct mib_node* const)&snmp_scalar, (struct mib_node* const)&snmp_scalar,
(struct mib_node* const)&snmp_scalar, (struct mib_node* const)&snmp_scalar,
(struct mib_node* const)&snmp_scalar, (struct mib_node* const)&snmp_scalar,
(struct mib_node* const)&snmp_scalar, (struct mib_node* const)&snmp_scalar
};
const struct mib_array_node snmp = {
&snmp_get_object_def,
&snmp_get_value,
&noleafs_get_object_def,
&noleafs_get_value,
MIB_NODE_AR,
28,
snmp_ids,
@ -150,24 +166,32 @@ const struct mib_array_node udpentry = {
udpentry_nodes
};
const s32_t udptable_id = 1;
struct mib_node* const udptable_node = (struct mib_node* const)&udpentry;
const struct mib_array_node udptable = {
s32_t udptable_id = 1;
struct mib_node* udptable_node = (struct mib_node* const)&udpentry;
struct mib_ram_array_node udptable = {
&noleafs_get_object_def,
&noleafs_get_value,
MIB_NODE_AR,
1,
MIB_NODE_RA,
0,
&udptable_id,
&udptable_node
};
const s32_t udp_ids[5] = { 1, 2, 3, 4, 5 };
struct mib_node* const udp_nodes[5] = {
NULL, NULL, NULL, NULL, (struct mib_node* const)&udptable
};
const struct mib_array_node udp = {
const mib_scalar_node udp_scalar = {
&udp_get_object_def,
&udp_get_value,
MIB_NODE_SC,
0
};
const s32_t udp_ids[5] = { 1, 2, 3, 4, 5 };
struct mib_node* const udp_nodes[5] = {
(struct mib_node* const)&udp_scalar, (struct mib_node* const)&udp_scalar,
(struct mib_node* const)&udp_scalar, (struct mib_node* const)&udp_scalar,
(struct mib_node* const)&udptable
};
const struct mib_array_node udp = {
&noleafs_get_object_def,
&noleafs_get_value,
MIB_NODE_AR,
5,
udp_ids,
@ -189,36 +213,52 @@ struct mib_list_rootnode tcpconntree_root = {
};
const s32_t tcpconnentry_ids[5] = { 1, 2, 3, 4, 5 };
struct mib_node* const tcpconnentry_nodes[5] = {
NULL, NULL, NULL, NULL, NULL
(struct mib_node* const)&tcpconntree_root, (struct mib_node* const)&tcpconntree_root,
(struct mib_node* const)&tcpconntree_root, (struct mib_node* const)&tcpconntree_root,
(struct mib_node* const)&tcpconntree_root
};
const struct mib_array_node tcpconnentry = {
&tcpconnentry_get_object_def,
&tcpconnentry_get_value,
&noleafs_get_object_def,
&noleafs_get_value,
MIB_NODE_AR,
5,
tcpconnentry_ids,
tcpconnentry_nodes
};
const s32_t tcpconntable_id = 1;
struct mib_node* const tcpconntable_node = (struct mib_node* const)&tcpconnentry;
const struct mib_array_node tcpconntable = {
s32_t tcpconntable_id = 1;
struct mib_node* tcpconntable_node = (struct mib_node* const)&tcpconnentry;
struct mib_ram_array_node tcpconntable = {
&noleafs_get_object_def,
&noleafs_get_value,
MIB_NODE_AR,
1,
MIB_NODE_RA,
/** @todo update maxlength when inserting / deleting from table
0 when table is empty, 1 when more than one entry */
0,
&tcpconntable_id,
&tcpconntable_node
};
const s32_t tcp_ids[15] = { 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15 };
struct mib_node* const tcp_nodes[15] = {
NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL,
(struct mib_node* const)&tcpconntable, NULL, NULL
};
const struct mib_array_node tcp = {
const mib_scalar_node tcp_scalar = {
&tcp_get_object_def,
&tcp_get_value,
MIB_NODE_SC,
0
};
const s32_t tcp_ids[15] = { 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15 };
struct mib_node* const tcp_nodes[15] = {
(struct mib_node* const)&tcp_scalar, (struct mib_node* const)&tcp_scalar,
(struct mib_node* const)&tcp_scalar, (struct mib_node* const)&tcp_scalar,
(struct mib_node* const)&tcp_scalar, (struct mib_node* const)&tcp_scalar,
(struct mib_node* const)&tcp_scalar, (struct mib_node* const)&tcp_scalar,
(struct mib_node* const)&tcp_scalar, (struct mib_node* const)&tcp_scalar,
(struct mib_node* const)&tcp_scalar, (struct mib_node* const)&tcp_scalar,
(struct mib_node* const)&tcpconntable, (struct mib_node* const)&tcp_scalar,
(struct mib_node* const)&tcp_scalar
};
const struct mib_array_node tcp = {
&noleafs_get_object_def,
&noleafs_get_value,
MIB_NODE_AR,
15,
tcp_ids,
@ -227,14 +267,31 @@ const struct mib_array_node tcp = {
#endif
/* icmp .1.3.6.1.2.1.5 */
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 };
struct mib_node* const icmp_nodes[26] = {
NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL,
NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL
};
const struct mib_array_node icmp = {
const mib_scalar_node icmp_scalar = {
&icmp_get_object_def,
&icmp_get_value,
MIB_NODE_SC,
0
};
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 };
struct mib_node* const icmp_nodes[26] = {
(struct mib_node* const)&icmp_scalar, (struct mib_node* const)&icmp_scalar,
(struct mib_node* const)&icmp_scalar, (struct mib_node* const)&icmp_scalar,
(struct mib_node* const)&icmp_scalar, (struct mib_node* const)&icmp_scalar,
(struct mib_node* const)&icmp_scalar, (struct mib_node* const)&icmp_scalar,
(struct mib_node* const)&icmp_scalar, (struct mib_node* const)&icmp_scalar,
(struct mib_node* const)&icmp_scalar, (struct mib_node* const)&icmp_scalar,
(struct mib_node* const)&icmp_scalar, (struct mib_node* const)&icmp_scalar,
(struct mib_node* const)&icmp_scalar, (struct mib_node* const)&icmp_scalar,
(struct mib_node* const)&icmp_scalar, (struct mib_node* const)&icmp_scalar,
(struct mib_node* const)&icmp_scalar, (struct mib_node* const)&icmp_scalar,
(struct mib_node* const)&icmp_scalar, (struct mib_node* const)&icmp_scalar,
(struct mib_node* const)&icmp_scalar, (struct mib_node* const)&icmp_scalar,
(struct mib_node* const)&icmp_scalar, (struct mib_node* const)&icmp_scalar
};
const struct mib_array_node icmp = {
&noleafs_get_object_def,
&noleafs_get_value,
MIB_NODE_AR,
26,
icmp_ids,
@ -265,13 +322,13 @@ const struct mib_array_node ipntomentry = {
ipntomentry_nodes
};
const s32_t ipntomtable_id = 1;
struct mib_node* const ipntomtable_node = (struct mib_node* const)&ipntomentry;
const struct mib_array_node ipntomtable = {
s32_t ipntomtable_id = 1;
struct mib_node* ipntomtable_node = (struct mib_node* const)&ipntomentry;
struct mib_ram_array_node ipntomtable = {
&noleafs_get_object_def,
&noleafs_get_value,
MIB_NODE_AR,
1,
MIB_NODE_RA,
0,
&ipntomtable_id,
&ipntomtable_node
};
@ -305,13 +362,13 @@ const struct mib_array_node iprteentry = {
iprteentry_nodes
};
const s32_t iprtetable_id = 1;
struct mib_node* const iprtetable_node = (struct mib_node* const)&iprteentry;
const struct mib_array_node iprtetable = {
s32_t iprtetable_id = 1;
struct mib_node* iprtetable_node = (struct mib_node* const)&iprteentry;
struct mib_ram_array_node iprtetable = {
&noleafs_get_object_def,
&noleafs_get_value,
MIB_NODE_AR,
1,
MIB_NODE_RA,
0,
&iprtetable_id,
&iprtetable_node
};
@ -343,27 +400,42 @@ const struct mib_array_node ipaddrentry = {
ipaddrentry_nodes
};
const s32_t ipaddrtable_id = 1;
struct mib_node* const ipaddrtable_node = (struct mib_node* const)&ipaddrentry;
const struct mib_array_node ipaddrtable = {
s32_t ipaddrtable_id = 1;
struct mib_node* ipaddrtable_node = (struct mib_node* const)&ipaddrentry;
struct mib_ram_array_node ipaddrtable = {
&noleafs_get_object_def,
&noleafs_get_value,
MIB_NODE_AR,
1,
MIB_NODE_RA,
0,
&ipaddrtable_id,
&ipaddrtable_node
};
/* ip .1.3.6.1.2.1.4 */
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 };
struct mib_node* const ip_nodes[23] = {
NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL,
NULL, NULL, NULL, NULL, NULL, NULL, NULL, (struct mib_node* const)&ipaddrtable,
(struct mib_node* const)&iprtetable, (struct mib_node* const)&ipntomtable, NULL
};
const struct mib_array_node ip = {
const mib_scalar_node ip_scalar = {
&ip_get_object_def,
&ip_get_value,
MIB_NODE_SC,
0
};
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 };
struct mib_node* const ip_nodes[23] = {
(struct mib_node* const)&ip_scalar, (struct mib_node* const)&ip_scalar,
(struct mib_node* const)&ip_scalar, (struct mib_node* const)&ip_scalar,
(struct mib_node* const)&ip_scalar, (struct mib_node* const)&ip_scalar,
(struct mib_node* const)&ip_scalar, (struct mib_node* const)&ip_scalar,
(struct mib_node* const)&ip_scalar, (struct mib_node* const)&ip_scalar,
(struct mib_node* const)&ip_scalar, (struct mib_node* const)&ip_scalar,
(struct mib_node* const)&ip_scalar, (struct mib_node* const)&ip_scalar,
(struct mib_node* const)&ip_scalar, (struct mib_node* const)&ip_scalar,
(struct mib_node* const)&ip_scalar, (struct mib_node* const)&ip_scalar,
(struct mib_node* const)&ip_scalar, (struct mib_node* const)&ipaddrtable,
(struct mib_node* const)&iprtetable, (struct mib_node* const)&ipntomtable,
(struct mib_node* const)&ip_scalar
};
const struct mib_array_node ip = {
&noleafs_get_object_def,
&noleafs_get_value,
MIB_NODE_AR,
23,
ip_ids,
@ -407,13 +479,13 @@ const struct mib_array_node attable = {
};
/* at .1.3.6.1.2.1.3 */
const s32_t at_id = 1;
struct mib_node* const at_node = (struct mib_node* const)&attable;
const struct mib_array_node at = {
s32_t at_id = 1;
struct mib_node* at_node = (struct mib_node* const)&attable;
struct mib_ram_array_node at = {
&noleafs_get_object_def,
&noleafs_get_value,
MIB_NODE_AR,
1,
MIB_NODE_RA,
0,
&at_id,
&at_node
};
@ -451,37 +523,57 @@ const struct mib_array_node ifentry = {
ifentry_nodes
};
const s32_t iftable_id = 1;
struct mib_node* const iftable_node = (struct mib_node* const)&ifentry;
const struct mib_array_node iftable = {
s32_t iftable_id = 1;
struct mib_node* iftable_node = (struct mib_node* const)&ifentry;
struct mib_ram_array_node iftable = {
&noleafs_get_object_def,
&noleafs_get_value,
MIB_NODE_AR,
1,
MIB_NODE_RA,
0,
&iftable_id,
&iftable_node
};
/* interfaces .1.3.6.1.2.1.2 */
const s32_t interfaces_ids[2] = { 1, 2 };
struct mib_node* const interfaces_nodes[2] = { NULL, (struct mib_node* const)&iftable };
const struct mib_array_node interfaces = {
const mib_scalar_node interfaces_scalar = {
&interfaces_get_object_def,
&interfaces_get_value,
MIB_NODE_SC,
0
};
const s32_t interfaces_ids[2] = { 1, 2 };
struct mib_node* const interfaces_nodes[2] = {
(struct mib_node* const)&interfaces_scalar, (struct mib_node* const)&iftable
};
const struct mib_array_node interfaces = {
&noleafs_get_object_def,
&noleafs_get_value,
MIB_NODE_AR,
2,
interfaces_ids,
interfaces_nodes
};
/* 0 1 2 3 4 5 6 */
/* system .1.3.6.1.2.1.1 */
const s32_t sys_tem_ids[7] = { 1, 2, 3, 4, 5, 6, 7 };
struct mib_node* const sys_tem_nodes[7] = { NULL, NULL, NULL, NULL, NULL, NULL, NULL };
/* work around name issue with 'sys_tem', some compiler(s?) seem to reserve 'system' */
const struct mib_array_node sys_tem = {
const mib_scalar_node sys_tem_scalar = {
&system_get_object_def,
&system_get_value,
MIB_NODE_SC,
0
};
const s32_t sys_tem_ids[7] = { 1, 2, 3, 4, 5, 6, 7 };
struct mib_node* const sys_tem_nodes[7] = {
(struct mib_node* const)&sys_tem_scalar, (struct mib_node* const)&sys_tem_scalar,
(struct mib_node* const)&sys_tem_scalar, (struct mib_node* const)&sys_tem_scalar,
(struct mib_node* const)&sys_tem_scalar, (struct mib_node* const)&sys_tem_scalar,
(struct mib_node* const)&sys_tem_scalar
};
/* work around name issue with 'sys_tem', some compiler(s?) seem to reserve 'system' */
const struct mib_array_node sys_tem = {
&noleafs_get_object_def,
&noleafs_get_value,
MIB_NODE_AR,
7,
sys_tem_ids,
@ -869,11 +961,15 @@ void snmp_inc_iflist(void)
struct mib_list_node *if_node = NULL;
snmp_mib_node_insert(&iflist_root, iflist_root.count + 1, &if_node);
/* enable getnext traversal on filled table */
iftable.maxlength = 1;
}
void snmp_dec_iflist(void)
{
snmp_mib_node_delete(&iflist_root, iflist_root.tail);
/* disable getnext traversal on empty table */
if(iflist_root.count == 0) iftable.maxlength = 0;
}
/**
@ -934,6 +1030,9 @@ void snmp_insert_arpidx_tree(struct netif *ni, struct ip_addr *ip)
}
}
}
/* enable getnext traversal on filled tables */
at.maxlength = 1;
ipntomtable.maxlength = 1;
}
/**
@ -1005,6 +1104,9 @@ void snmp_delete_arpidx_tree(struct netif *ni, struct ip_addr *ip)
}
}
}
/* disable getnext traversal on empty tables */
if(arptree_root.count == 0) at.maxlength = 0;
if(ipntomtree_root.count == 0) ipntomtable.maxlength = 0;
}
void snmp_inc_ipinreceives(void)
@ -1133,6 +1235,8 @@ void snmp_insert_ipaddridx_tree(struct netif *ni)
}
level++;
}
/* enable getnext traversal on filled table */
ipaddrtable.maxlength = 1;
}
/**
@ -1194,6 +1298,8 @@ void snmp_delete_ipaddridx_tree(struct netif *ni)
snmp_mib_lrn_free(next);
}
}
/* disable getnext traversal on empty table */
if (ipaddrtree_root.count == 0) ipaddrtable.maxlength = 0;
}
/**
@ -1258,6 +1364,8 @@ void snmp_insert_iprteidx_tree(u8_t dflt, struct netif *ni)
level++;
}
}
/* enable getnext traversal on filled table */
iprtetable.maxlength = 1;
}
/**
@ -1338,6 +1446,8 @@ void snmp_delete_iprteidx_tree(u8_t dflt, struct netif *ni)
}
}
}
/* disable getnext traversal on empty table */
if (iprtetree_root.count == 0) iprtetable.maxlength = 0;
}
@ -1576,6 +1686,7 @@ void snmp_insert_udpidx_tree(struct udp_pcb *pcb)
}
}
}
udptable.maxlength = 1;
}
/**
@ -1588,56 +1699,75 @@ void snmp_delete_udpidx_tree(struct udp_pcb *pcb)
struct mib_list_node *udp_n, *del_n[5];
struct ip_addr ip;
s32_t udpidx[5];
u8_t fc, level, del_cnt;
u8_t bindings, fc, level, del_cnt;
LWIP_ASSERT("pcb != NULL", pcb != NULL);
ip.addr = ntohl(pcb->local_ip.addr);
snmp_iptooid(&ip, &udpidx[0]);
udpidx[4] = pcb->local_port;
/* mark nodes for deletion */
level = 0;
del_cnt = 0;
udp_rn = &udp_root;
while ((level < 5) && (udp_rn != NULL))
{
fc = snmp_mib_node_find(udp_rn, udpidx[level], &udp_n);
if (fc == 0)
/* count PCBs for a given binding
(e.g. when reusing ports or for temp output PCBs) */
bindings = 0;
pcb = udp_pcbs;
while ((pcb != NULL))
{
if ((pcb->local_ip.addr == ip.addr) &&
(pcb->local_port == udpidx[4]))
{
/* udpidx[level] does not exist */
del_cnt = 0;
udp_rn = NULL;
bindings++;
}
else if (fc == 1)
{
del_rn[del_cnt] = udp_rn;
del_n[del_cnt] = udp_n;
del_cnt++;
udp_rn = (struct mib_list_rootnode*)(udp_n->nptr);
}
else if (fc == 2)
{
/* reset delete (2 or more childs) */
del_cnt = 0;
udp_rn = (struct mib_list_rootnode*)(udp_n->nptr);
}
level++;
pcb = pcb->next;
}
/* delete marked index nodes */
while (del_cnt > 0)
if (bindings == 1)
{
del_cnt--;
udp_rn = del_rn[del_cnt];
udp_n = del_n[del_cnt];
/* selectively remove */
/* mark nodes for deletion */
level = 0;
del_cnt = 0;
udp_rn = &udp_root;
while ((level < 5) && (udp_rn != NULL))
{
fc = snmp_mib_node_find(udp_rn, udpidx[level], &udp_n);
if (fc == 0)
{
/* udpidx[level] does not exist */
del_cnt = 0;
udp_rn = NULL;
}
else if (fc == 1)
{
del_rn[del_cnt] = udp_rn;
del_n[del_cnt] = udp_n;
del_cnt++;
udp_rn = (struct mib_list_rootnode*)(udp_n->nptr);
}
else if (fc == 2)
{
/* reset delete (2 or more childs) */
del_cnt = 0;
udp_rn = (struct mib_list_rootnode*)(udp_n->nptr);
}
level++;
}
/* delete marked index nodes */
while (del_cnt > 0)
{
del_cnt--;
udp_rn = del_rn[del_cnt];
udp_n = del_n[del_cnt];
next = snmp_mib_node_delete(udp_rn, udp_n);
if (next != NULL)
{
LWIP_ASSERT("next_count == 0",next->count == 0);
snmp_mib_lrn_free(next);
next = snmp_mib_node_delete(udp_rn, udp_n);
if (next != NULL)
{
LWIP_ASSERT("next_count == 0",next->count == 0);
snmp_mib_lrn_free(next);
}
}
}
/* disable getnext traversal on empty table */
if (udp_root.count == 0) udptable.maxlength = 0;
}
@ -1817,7 +1947,10 @@ system_get_object_def(u8_t ident_len, s32_t *ident, struct obj_def *od)
{
u8_t id;
if ((ident_len == 2) && (ident[1] == 0))
/* return to object name, adding index depth (1) */
ident_len += 1;
ident -= 1;
if (ident_len == 2)
{
od->id_inst_len = ident_len;
od->id_inst_ptr = ident;
@ -1938,7 +2071,10 @@ system_get_value(struct obj_def *od, u16_t len, void *value)
static void
interfaces_get_object_def(u8_t ident_len, s32_t *ident, struct obj_def *od)
{
if ((ident_len == 2) && (ident[0] == 1) && (ident[1] == 0))
/* return to object name, adding index depth (1) */
ident_len += 1;
ident -= 1;
if (ident_len == 2)
{
od->id_inst_len = ident_len;
od->id_inst_ptr = ident;
@ -2329,7 +2465,10 @@ ip_get_object_def(u8_t ident_len, s32_t *ident, struct obj_def *od)
{
u8_t id;
if ((ident_len == 2) && (ident[1] == 0))
/* return to object name, adding index depth (1) */
ident_len += 1;
ident -= 1;
if (ident_len == 2)
{
od->id_inst_len = ident_len;
od->id_inst_ptr = ident;
@ -2967,7 +3106,10 @@ ip_ntomentry_get_value(struct obj_def *od, u16_t len, void *value)
static void
icmp_get_object_def(u8_t ident_len, s32_t *ident, struct obj_def *od)
{
if ((ident_len == 2) && (ident[1] == 0) &&
/* return to object name, adding index depth (1) */
ident_len += 1;
ident -= 1;
if ((ident_len == 2) &&
(ident[0] > 0) && (ident[0] < 27))
{
od->id_inst_len = ident_len;
@ -3083,7 +3225,10 @@ tcp_get_object_def(u8_t ident_len, s32_t *ident, struct obj_def *od)
{
u8_t id;
if ((ident_len == 2) && (ident[1] == 0))
/* return to object name, adding index depth (1) */
ident_len += 1;
ident -= 1;
if (ident_len == 2)
{
od->id_inst_len = ident_len;
od->id_inst_ptr = ident;
@ -3282,7 +3427,10 @@ tcpconnentry_get_value(struct obj_def *od, u16_t len, void *value)
static void
udp_get_object_def(u8_t ident_len, s32_t *ident, struct obj_def *od)
{
if ((ident_len == 2) && (ident[1] == 0) &&
/* return to object name, adding index depth (1) */
ident_len += 1;
ident -= 1;
if ((ident_len == 2) &&
(ident[0] > 0) && (ident[0] < 6))
{
od->id_inst_len = ident_len;
@ -3409,7 +3557,10 @@ udpentry_get_value(struct obj_def *od, u16_t len, void *value)
static void
snmp_get_object_def(u8_t ident_len, s32_t *ident, struct obj_def *od)
{
if ((ident_len == 2) && (ident[1] == 0))
/* return to object name, adding index depth (1) */
ident_len += 1;
ident -= 1;
if (ident_len == 2)
{
u8_t id;

View File

@ -437,6 +437,8 @@ snmp_mib_node_delete(struct mib_list_rootnode *rn, struct mib_list_node *n)
return next;
}
/**
* Searches tree for the supplied (scalar?) object identifier.
*
@ -544,7 +546,7 @@ snmp_search_tree(struct mib_node *node, u8_t ident_len, s32_t *ident, struct obj
else
{
/* search failed, object id points to unknown object (nosuchname) */
LWIP_DEBUGF(SNMP_MIB_DEBUG,("search failed, object not in this MIB"));
LWIP_DEBUGF(SNMP_MIB_DEBUG,("search failed, object not in this MIB\n"));
return NULL;
}
}
@ -615,6 +617,23 @@ snmp_search_tree(struct mib_node *node, u8_t ident_len, s32_t *ident, struct obj
return NULL;
}
}
else if (node_type == MIB_NODE_SC)
{
mib_scalar_node *sn;
sn = (mib_scalar_node *)node;
if ((ident_len == 1) && (*ident == 0))
{
sn->get_object_def(ident_len, ident, object_def);
return (struct mib_node*)sn;
}
else
{
/* search failed, short object identifier (nosuchname) */
LWIP_DEBUGF(SNMP_MIB_DEBUG,("search failed, short object identifier\n"));
return NULL;
}
}
else
{
/* unknown node_type */
@ -627,11 +646,42 @@ snmp_search_tree(struct mib_node *node, u8_t ident_len, s32_t *ident, struct obj
return NULL;
}
/**
* Test table for presence of at least one table entry.
*/
static u8_t
empty_table(struct mib_node *node)
{
u8_t node_type;
u8_t empty = 0;
if (node != NULL)
{
node_type = node->node_type;
if (node_type == MIB_NODE_LR)
{
struct mib_list_rootnode *lrn;
lrn = (struct mib_list_rootnode *)node;
if ((lrn->count == 0) || (lrn->head == NULL))
{
empty = 1;
}
}
else if ((node_type == MIB_NODE_AR) || (node_type == MIB_NODE_RA))
{
struct mib_array_node *an;
an = (struct mib_array_node *)node;
if ((an->maxlength == 0) || (an->nptr == NULL))
{
empty = 1;
}
}
}
return empty;
}
/**
* Tree expansion.
*
* @todo function ptrs for tabular items
* if not empty add first index, nextThing.0 otherwise
*/
struct mib_node *
snmp_expand_tree(struct mib_node *node, u8_t ident_len, s32_t *ident, struct snmp_obj_id *oidret)
@ -669,49 +719,12 @@ snmp_expand_tree(struct mib_node *node, u8_t ident_len, s32_t *ident, struct snm
if (an->nptr[i] == NULL)
{
LWIP_DEBUGF(SNMP_MIB_DEBUG,("leaf node\n"));
/* leaf node,
if scalar: if ident_len == 1 add '.0', nextThing.0 otherwise */
if (ident_len == 1)
{
oidret->id[oidret->len] = 0;
(oidret->len)++;
LWIP_DEBUGF(SNMP_MIB_DEBUG,("ident_len == 1, added .0\n"));
return (struct mib_node*)an;
}
else if ((i + 1) < an->maxlength)
/* leaf node (e.g. in a fixed size table) */
if ((i + 1) < an->maxlength)
{
(oidret->len)--;
oidret->id[oidret->len] = an->objid[i + 1];
(oidret->len)++;
if (an->nptr[i + 1] == NULL)
{
oidret->id[oidret->len] = 0;
(oidret->len)++;
LWIP_DEBUGF(SNMP_MIB_DEBUG,("(i + 1) < an->maxlength\n"));
return (struct mib_node*)an;
}
else
{
struct nse cur_node;
LWIP_DEBUGF(SNMP_MIB_DEBUG,("non-leaf node\n"));
/* non-leaf, store right child ptr and id */
if ((i + 2) < an->maxlength)
{
cur_node.r_ptr = an->nptr[i + 2];
cur_node.r_id = an->objid[i + 2];
}
else
{
cur_node.r_ptr = NULL;
}
LWIP_DEBUGF(SNMP_MIB_DEBUG,("expand, push_node() node=%p id=%"S32_F"\n",(void*)cur_node.r_ptr,cur_node.r_id));
push_node(&cur_node);
/* follow next child pointer */
ident_len--;
ident++;
node = an->nptr[i+1];
}
(oidret->len)++;
}
else
{
@ -721,14 +734,20 @@ snmp_expand_tree(struct mib_node *node, u8_t ident_len, s32_t *ident, struct snm
}
else
{
u8_t j;
struct nse cur_node;
LWIP_DEBUGF(SNMP_MIB_DEBUG,("non-leaf node\n"));
/* non-leaf, store right child ptr and id */
if ((i + 1) < an->maxlength)
j = i + 1;
while ((j < an->maxlength) && (empty_table(an->nptr[j])))
{
cur_node.r_ptr = an->nptr[i + 1];
cur_node.r_id = an->objid[i + 1];
j++;
}
if (j < an->maxlength)
{
cur_node.r_ptr = an->nptr[j];
cur_node.r_id = an->objid[j];
}
else
{
@ -750,28 +769,38 @@ snmp_expand_tree(struct mib_node *node, u8_t ident_len, s32_t *ident, struct snm
}
else
{
/* ident_len == 0, complete object identifier */
/* add leftmost '.thing' */
oidret->id[oidret->len] = an->objid[0];
(oidret->len)++;
if (an->nptr[0] == NULL)
u8_t j;
/* ident_len == 0, complete with leftmost '.thing' */
j = 0;
while ((j < an->maxlength) && empty_table(an->nptr[j]))
{
/* leaf node
if scalar: add '.0' */
oidret->id[oidret->len] = 0;
j++;
}
if (j < an->maxlength)
{
LWIP_DEBUGF(SNMP_MIB_DEBUG,("left an->objid[j]==%"S32_F"\n",an->objid[j]));
oidret->id[oidret->len] = an->objid[j];
(oidret->len)++;
return (struct mib_node*)an;
if (an->nptr[j] == NULL)
{
/* leaf node */
return (struct mib_node*)an;
}
else
{
/* no leaf, continue */
node = an->nptr[j];
}
}
else
{
/* no leaf, continue */
node = an->nptr[0];
/* j == an->maxlength */
climb_tree = 1;
}
}
}
else if(node_type == MIB_NODE_LR)
{
/** @todo need this for indexing tables */
struct mib_list_rootnode *lrn;
struct mib_list_node *ln;
@ -793,7 +822,6 @@ snmp_expand_tree(struct mib_node *node, u8_t ident_len, s32_t *ident, struct snm
if (ln->nptr == NULL)
{
/* leaf node */
/** @todo if scalar: if ident_len == 1 add '.0', nextThing.0 otherwise */
if (ln->next != NULL)
{
(oidret->len)--;
@ -804,19 +832,25 @@ snmp_expand_tree(struct mib_node *node, u8_t ident_len, s32_t *ident, struct snm
}
else
{
(oidret->len)--;
(oidret->len)--;
climb_tree = 1;
}
}
else
{
struct mib_list_node *jn;
struct nse cur_node;
/* non-leaf, store right child ptr and id */
if (ln->next != NULL)
jn = ln->next;
while ((jn != NULL) && empty_table(jn->nptr))
{
cur_node.r_ptr = ln->next->nptr;
cur_node.r_id = ln->next->objid;
jn = jn->next;
}
if (jn != NULL)
{
cur_node.r_ptr = jn->nptr;
cur_node.r_id = jn->objid;
}
else
{
@ -839,24 +873,58 @@ snmp_expand_tree(struct mib_node *node, u8_t ident_len, s32_t *ident, struct snm
}
else
{
/* ident_len == 0, complete object identifier */
/* add leftmost '.thing' */
oidret->id[oidret->len] = lrn->head->objid;
(oidret->len)++;
if (lrn->head->nptr == NULL)
struct mib_list_node *jn;
/* ident_len == 0, complete with leftmost '.thing' */
jn = lrn->head;
while ((jn != NULL) && empty_table(jn->nptr))
{
/* leaf node */
/* @todo problem: if scalar add .0 */
LWIP_DEBUGF(SNMP_MIB_DEBUG,("lrn->head->nptr == NULL\n"));
return (struct mib_node*)lrn;
jn = jn->next;
}
if (jn != NULL)
{
LWIP_DEBUGF(SNMP_MIB_DEBUG,("left jn->objid==%"S32_F"\n",jn->objid));
oidret->id[oidret->len] = jn->objid;
(oidret->len)++;
if (jn->nptr == NULL)
{
/* leaf node */
LWIP_DEBUGF(SNMP_MIB_DEBUG,("jn->nptr == NULL\n"));
return (struct mib_node*)lrn;
}
else
{
/* no leaf, continue */
node = jn->nptr;
}
}
else
{
/* no leaf, continue */
node = lrn->head->nptr;
/* jn == NULL */
climb_tree = 1;
}
}
}
else if(node_type == MIB_NODE_SC)
{
mib_scalar_node *sn;
/* scalar node */
sn = (mib_scalar_node *)node;
if (ident_len > 0)
{
/* at .0 */
climb_tree = 1;
}
else
{
/* ident_len == 0, complete object identifier */
oidret->id[oidret->len] = 0;
(oidret->len)++;
/* leaf node */
LWIP_DEBUGF(SNMP_MIB_DEBUG,("completed scalar leaf\n"));
return (struct mib_node*)sn;
}
}
else
{
/* unknown/unhandled node_type */

View File

@ -84,12 +84,12 @@ snmp_init(void)
struct snmp_msg_pstat *msg_ps;
u8_t i;
snmp1_pcb = udp_new();
if (snmp1_pcb != NULL)
{
udp_recv(snmp1_pcb, snmp_recv, (void *)SNMP_IN_PORT);
udp_bind(snmp1_pcb, IP_ADDR_ANY, SNMP_IN_PORT);
}
snmp1_pcb = udp_new();
if (snmp1_pcb != NULL)
{
udp_recv(snmp1_pcb, snmp_recv, (void *)SNMP_IN_PORT);
udp_bind(snmp1_pcb, IP_ADDR_ANY, SNMP_IN_PORT);
}
msg_ps = &msg_input_list[0];
for (i=0; i<SNMP_CONCURRENT_REQUESTS; i++)
{
@ -318,8 +318,6 @@ snmp_recv(void *arg, struct udp_pcb *pcb, struct pbuf *p, struct ip_addr *addr,
if (snmp_iso_prefix_expand(msg_ps->invb.head->ident_len, msg_ps->invb.head->ident, &oid))
{
/** @todo expand tree and complete oid */
#if 1
if (msg_ps->invb.head->ident_len > 3)
{
/* can offset ident_len and ident */
@ -332,9 +330,6 @@ snmp_recv(void *arg, struct udp_pcb *pcb, struct pbuf *p, struct ip_addr *addr,
/* can't offset ident_len -4, ident + 4 */
mn = snmp_expand_tree((struct mib_node*)&internet, 0, NULL, &oid);
}
#else
mn = (struct mib_node*)&internet;
#endif
}
else
{
@ -344,9 +339,12 @@ snmp_recv(void *arg, struct udp_pcb *pcb, struct pbuf *p, struct ip_addr *addr,
{
struct snmp_varbind *vb;
vb = snmp_varbind_alloc(&oid, (SNMP_ASN1_UNIV | SNMP_ASN1_PRIMIT | SNMP_ASN1_NUL), 0);
mn->get_object_def(1, &oid.id[oid.len - 1], &object_def);
vb = snmp_varbind_alloc(&oid, object_def.asn_type, object_def.v_len);
if (vb != NULL)
{
mn->get_value(&object_def, object_def.v_len, vb->value);
snmp_varbind_tail_add(&msg_ps->outvb, vb);
}
else

View File

@ -75,14 +75,16 @@ struct obj_def
s32_t *id_inst_ptr;
};
/** MIB const scalar (.0) node */
#define MIB_NODE_SC 0x01
/** MIB const array node */
#define MIB_NODE_AR 0x01
#define MIB_NODE_AR 0x02
/** MIB array node (mem_malloced from RAM) */
#define MIB_NODE_RA 0x02
#define MIB_NODE_RA 0x03
/** MIB list root node (mem_malloced from RAM) */
#define MIB_NODE_LR 0x03
#define MIB_NODE_LR 0x04
/** MIB node for external objects */
#define MIB_NODE_EX 0x04
#define MIB_NODE_EX 0x05
/** node "base class" layout, the mandatory fields for a node */
struct mib_node
@ -99,6 +101,9 @@ struct mib_node
const u16_t maxlength;
};
/** derived node for scalars .0 index */
typedef struct mib_node mib_scalar_node;
/** derived node, points to a fixed size const array
of sub-identifiers plus a 'child' pointer */
struct mib_array_node