Corrected object identifier codec for object ids not starting with .iso.dod (e.g. zeroDotZero (0.0)).

This commit is contained in:
christiaans 2006-08-07 11:32:44 +00:00
parent a82e02ef15
commit 7eeaf8eaa5
2 changed files with 130 additions and 72 deletions

View File

@ -420,6 +420,7 @@ snmp_asn1_dec_oid(struct pbuf *p, u16_t ofs, u16_t len, struct snmp_obj_id *oid)
{ {
u16_t plen, base; u16_t plen, base;
u8_t *msg_ptr; u8_t *msg_ptr;
s32_t *oid_ptr;
plen = 0; plen = 0;
while (p != NULL) while (p != NULL)
@ -431,13 +432,52 @@ snmp_asn1_dec_oid(struct pbuf *p, u16_t ofs, u16_t len, struct snmp_obj_id *oid)
msg_ptr = p->payload; msg_ptr = p->payload;
msg_ptr += ofs - base; msg_ptr += ofs - base;
if ((len > 1) && (*msg_ptr == 0x2B)) oid->len = 0;
oid_ptr = &oid->id[0];
if (len > 0)
{ {
s32_t *oid_ptr; /* first compressed octet */
if (*msg_ptr == 0x2B)
/* we have compressed 1.3 (iso.org) Z = (X * 40) + Y */ {
/* (most) common case 1.3 (iso.org) */
*oid_ptr = 1;
oid_ptr++;
*oid_ptr = 3;
oid_ptr++;
}
else if (*msg_ptr < 40)
{
*oid_ptr = 0;
oid_ptr++;
*oid_ptr = *msg_ptr;
oid_ptr++;
}
else if (*msg_ptr < 80)
{
*oid_ptr = 1;
oid_ptr++;
*oid_ptr = (*msg_ptr) - 40;
oid_ptr++;
}
else
{
*oid_ptr = 2;
oid_ptr++;
*oid_ptr = (*msg_ptr) - 80;
oid_ptr++;
}
oid->len = 2;
}
else
{
/* length == 0, zero length (empty list) isn't allowed here.
ISO 8825 (BER) isn't clear about this, but some seem to accept it (why?).
zeroDotZero (0.0) must be at least 06 01 00 */
return ERR_ARG;
}
len--; len--;
/* proceed to .dod */ if (len > 0)
{
ofs += 1; ofs += 1;
if (ofs >= plen) if (ofs >= plen)
{ {
@ -452,8 +492,7 @@ snmp_asn1_dec_oid(struct pbuf *p, u16_t ofs, u16_t len, struct snmp_obj_id *oid)
/* next octet in same pbuf */ /* next octet in same pbuf */
msg_ptr++; msg_ptr++;
} }
oid->len = 0; }
oid_ptr = &oid->id[0];
while ((len > 0) && (oid->len < LWIP_SNMP_OBJ_ID_LEN)) while ((len > 0) && (oid->len < LWIP_SNMP_OBJ_ID_LEN))
{ {
/* sub-identifier uses multiple octets */ /* sub-identifier uses multiple octets */
@ -525,12 +564,7 @@ snmp_asn1_dec_oid(struct pbuf *p, u16_t ofs, u16_t len, struct snmp_obj_id *oid)
/* len > 0, oid->len == LWIP_SNMP_OBJ_ID_LEN or malformed encoding */ /* len > 0, oid->len == LWIP_SNMP_OBJ_ID_LEN or malformed encoding */
return ERR_ARG; return ERR_ARG;
} }
}
else
{
/* length <= 1 OR prefix not 1.3 (iso.org) */
return ERR_ARG;
}
} }
p = p->next; p = p->next;
} }

View File

@ -143,6 +143,13 @@ snmp_asn1_enc_oid_cnt(u8_t ident_len, s32_t *ident, u16_t *octets_needed)
u8_t cnt; u8_t cnt;
cnt = 0; cnt = 0;
if (ident_len > 1)
{
/* compressed prefix in one octet */
cnt++;
ident_len -= 2;
ident += 2;
}
while(ident_len > 0) while(ident_len > 0)
{ {
ident_len--; ident_len--;
@ -157,8 +164,6 @@ snmp_asn1_enc_oid_cnt(u8_t ident_len, s32_t *ident, u16_t *octets_needed)
} }
ident++; ident++;
} }
/* one extra for compressed iso.dod. prefix */
cnt++;
*octets_needed = cnt; *octets_needed = cnt;
} }
@ -445,8 +450,19 @@ snmp_asn1_enc_oid(struct pbuf *p, u16_t ofs, u8_t ident_len, s32_t *ident)
{ {
msg_ptr = p->payload; msg_ptr = p->payload;
msg_ptr += ofs - base; msg_ptr += ofs - base;
/* add compressed prefix .iso.dod */
if (ident_len > 1)
{
if ((ident[0] == 1) && (ident[1] == 3))
{
/* compressed (most common) prefix .iso.dod */
*msg_ptr = 0x2b; *msg_ptr = 0x2b;
}
else
{
/* calculate prefix */
*msg_ptr = (ident[0] * 40) + ident[1];
}
ofs += 1; ofs += 1;
if (ofs >= plen) if (ofs >= plen)
{ {
@ -461,6 +477,14 @@ snmp_asn1_enc_oid(struct pbuf *p, u16_t ofs, u8_t ident_len, s32_t *ident)
/* next octet in same pbuf */ /* next octet in same pbuf */
msg_ptr++; msg_ptr++;
} }
ident_len -= 2;
ident += 2;
}
else
{
/* ident_len <= 1, at least we need zeroDotZero (0.0) (ident_len == 2) */
return ERR_ARG;
}
while (ident_len > 0) while (ident_len > 0)
{ {
s32_t sub_id; s32_t sub_id;