forked from osmocom/wireshark
Add support for RELATIVE-OID ASN.1 type. Bug 9192 (https://bugs.wireshark.org/bugzilla/show_bug.cgi?id=9192)
From Ed Beroset. svn path=/trunk/; revision=52393
This commit is contained in:
parent
625fbd5f9a
commit
ee208c8dcc
|
@ -113,7 +113,8 @@ FIELDTYPE FT_NONE, FT_BOOLEAN, FT_UINT8, FT_UINT16, FT_UINT24,
|
|||
FT_INT64, FT_FLOAT, FT_DOUBLE, FT_ABSOLUTE_TIME,
|
||||
FT_RELATIVE_TIME, FT_STRING, FT_STRINGZ, FT_EUI64,
|
||||
FT_UINT_STRING, FT_ETHER, FT_BYTES, FT_UINT_BYTES, FT_IPv4,
|
||||
FT_IPv6, FT_IPXNET, FT_FRAMENUM, FT_PROTOCOL, FT_GUID, FT_OID
|
||||
FT_IPv6, FT_IPXNET, FT_FRAMENUM, FT_PROTOCOL, FT_GUID, FT_OID,
|
||||
FT_REL_OID
|
||||
FIELDDISPLAY --For FT_UINT{8,16,24,32,64} and FT_INT{8,16,24,32,64):
|
||||
|
||||
BASE_DEC, BASE_HEX, BASE_OCT, BASE_DEC_HEX, BASE_HEX_DEC,
|
||||
|
@ -725,6 +726,7 @@ The type of value this field holds. The current field types are:
|
|||
address.
|
||||
FT_GUID A Globally Unique Identifier
|
||||
FT_OID An ASN.1 Object Identifier
|
||||
FT_REL_OID An ASN.1 Relative Object Identifier
|
||||
FT_EUI64 A EUI-64 Address
|
||||
|
||||
Some of these field types are still not handled in the display filter
|
||||
|
@ -1331,8 +1333,8 @@ proto_register_*() function) and a value. The value will be fetched
|
|||
from the tvbuff by proto_tree_add_item(), based on the type of the field
|
||||
and the encoding of the value as specified by the "encoding" argument.
|
||||
|
||||
For FT_NONE, FT_BYTES, FT_ETHER, FT_IPv6, FT_IPXNET, FT_OID fields,
|
||||
and 'protocol' fields the encoding is not relevant; the 'encoding'
|
||||
For FT_NONE, FT_BYTES, FT_ETHER, FT_IPv6, FT_IPXNET, FT_OID, FT_REL_OID
|
||||
fields, and 'protocol' fields the encoding is not relevant; the 'encoding'
|
||||
argument should be ENC_NA (Not Applicable).
|
||||
|
||||
For integral, floating-point, Boolean, FT_GUID, and FT_EUI64 fields,
|
||||
|
|
|
@ -45,6 +45,7 @@ use Getopt::Std;
|
|||
'FT_PCRE', 'Perl Compatible Regular Expression',
|
||||
'FT_GUID', 'Globally Unique Identifier',
|
||||
'FT_OID', 'Object Identifier',
|
||||
'FT_REL_OID', 'Relative Object Identifier',
|
||||
);
|
||||
|
||||
getopts('e');
|
||||
|
|
|
@ -43,6 +43,7 @@
|
|||
'FT_PCRE', 'Perl Compatible Regular Expression',
|
||||
'FT_GUID', 'Globally Unique Identifier',
|
||||
'FT_OID', 'Object Identifier',
|
||||
'FT_REL_OID', 'Relative Object Identifier',
|
||||
);
|
||||
|
||||
# Read all the data into memory
|
||||
|
|
|
@ -83,8 +83,9 @@ compatible_ftypes(ftenum_t a, ftenum_t b)
|
|||
case FT_OID:
|
||||
case FT_AX25:
|
||||
case FT_VINES:
|
||||
case FT_REL_OID:
|
||||
|
||||
return (b == FT_ETHER || b == FT_BYTES || b == FT_UINT_BYTES || b == FT_GUID || b == FT_OID || b == FT_AX25 || b == FT_VINES);
|
||||
return (b == FT_ETHER || b == FT_BYTES || b == FT_UINT_BYTES || b == FT_GUID || b == FT_OID || b == FT_AX25 || b == FT_VINES || b == FT_REL_OID);
|
||||
|
||||
case FT_BOOLEAN:
|
||||
case FT_FRAMENUM:
|
||||
|
@ -189,6 +190,7 @@ mk_fvalue_from_val_string(header_field_info *hfinfo, char *s)
|
|||
case FT_PCRE:
|
||||
case FT_GUID:
|
||||
case FT_OID:
|
||||
case FT_REL_OID:
|
||||
return NULL;
|
||||
|
||||
case FT_BOOLEAN:
|
||||
|
@ -296,6 +298,7 @@ is_bytes_type(enum ftenum type)
|
|||
case FT_IPv6:
|
||||
case FT_GUID:
|
||||
case FT_OID:
|
||||
case FT_REL_OID:
|
||||
return TRUE;
|
||||
|
||||
case FT_NONE:
|
||||
|
|
|
@ -849,6 +849,9 @@ try_dissect_unknown_ber(packet_info *pinfo, tvbuff_t *tvb, volatile int offset,
|
|||
case BER_UNI_TAG_OID:
|
||||
offset = dissect_ber_object_identifier_str(FALSE, &asn1_ctx, tree, tvb, start_offset, hf_ber_unknown_OID, NULL);
|
||||
break;
|
||||
case BER_UNI_TAG_RELATIVE_OID:
|
||||
offset = dissect_ber_relative_oid_str(FALSE, &asn1_ctx, tree, tvb, start_offset, hf_ber_unknown_OID, NULL);
|
||||
break;
|
||||
case BER_UNI_TAG_NumericString:
|
||||
offset = dissect_ber_octet_string(FALSE, &asn1_ctx, tree, tvb, start_offset, hf_ber_unknown_NumericString, NULL);
|
||||
break;
|
||||
|
@ -3229,7 +3232,6 @@ dissect_ber_choice(asn1_ctx_t *actx, proto_tree *parent_tree, tvbuff_t *tvb, int
|
|||
#ifdef DEBUG_BER_CHOICE
|
||||
{
|
||||
const char *name;
|
||||
header_field_info *hfinfo;
|
||||
if (hf_id >= 0) {
|
||||
hfinfo = proto_registrar_get_nth(hf_id);
|
||||
name = hfinfo->name;
|
||||
|
@ -3356,7 +3358,6 @@ printf("CHOICE testing potential subdissector class[%p]:%d:(expected)%d tag:%d:
|
|||
#ifdef DEBUG_BER_CHOICE
|
||||
{
|
||||
const char *name;
|
||||
header_field_info *hfinfo;
|
||||
if (hf_id >= 0) {
|
||||
hfinfo = proto_registrar_get_nth(hf_id);
|
||||
name = hfinfo->name;
|
||||
|
@ -3381,7 +3382,6 @@ printf("CHOICE dissect_ber_choice(%s) calling subdissector len:%d\n", name, tvb_
|
|||
#ifdef DEBUG_BER_CHOICE
|
||||
{
|
||||
const char *name;
|
||||
header_field_info *hfinfo;
|
||||
if (hf_id >= 0) {
|
||||
hfinfo = proto_registrar_get_nth(hf_id);
|
||||
name = hfinfo->name;
|
||||
|
@ -3397,7 +3397,6 @@ printf("CHOICE dissect_ber_choice(%s) subdissector ate %d bytes\n", name, count)
|
|||
#ifdef DEBUG_BER_CHOICE
|
||||
{
|
||||
const char *name;
|
||||
header_field_info *hfinfo;
|
||||
if (hf_id >= 0) {
|
||||
hfinfo = proto_registrar_get_nth(hf_id);
|
||||
name = hfinfo->name;
|
||||
|
@ -3465,7 +3464,6 @@ dissect_ber_old_choice(asn1_ctx_t *actx, proto_tree *parent_tree, tvbuff_t *tvb,
|
|||
#ifdef DEBUG_BER_CHOICE
|
||||
{
|
||||
const char *name;
|
||||
header_field_info *hfinfo;
|
||||
if (hf_id >= 0) {
|
||||
hfinfo = proto_registrar_get_nth(hf_id);
|
||||
name = hfinfo->name;
|
||||
|
@ -3592,7 +3590,6 @@ printf("CHOICE testing potential subdissector class[%p]:%d:(expected)%d tag:%d:
|
|||
#ifdef DEBUG_BER_CHOICE
|
||||
{
|
||||
const char *name;
|
||||
header_field_info *hfinfo;
|
||||
if (hf_id >= 0) {
|
||||
hfinfo = proto_registrar_get_nth(hf_id);
|
||||
name = hfinfo->name;
|
||||
|
@ -3614,7 +3611,6 @@ printf("CHOICE dissect_ber_old_choice(%s) calling subdissector len:%d\n", name,
|
|||
#ifdef DEBUG_BER_CHOICE
|
||||
{
|
||||
const char *name;
|
||||
header_field_info *hfinfo;
|
||||
if (hf_id >= 0) {
|
||||
hfinfo = proto_registrar_get_nth(hf_id);
|
||||
name = hfinfo->name;
|
||||
|
@ -3630,7 +3626,6 @@ printf("CHOICE dissect_ber_old_choice(%s) subdissector ate %d bytes\n", name, co
|
|||
#ifdef DEBUG_BER_CHOICE
|
||||
{
|
||||
const char *name;
|
||||
header_field_info *hfinfo;
|
||||
if (hf_id >= 0) {
|
||||
hfinfo = proto_registrar_get_nth(hf_id);
|
||||
name = hfinfo->name;
|
||||
|
@ -3833,6 +3828,110 @@ dissect_ber_GeneralString(asn1_ctx_t *actx, proto_tree *tree, tvbuff_t *tvb, int
|
|||
return offset;
|
||||
}
|
||||
|
||||
/* 8.19 Encoding of a relative object identifier value.
|
||||
*/
|
||||
int
|
||||
dissect_ber_relative_oid(gboolean implicit_tag, asn1_ctx_t *actx, proto_tree *tree, tvbuff_t *tvb, int offset, gint hf_id, tvbuff_t **value_tvb)
|
||||
{
|
||||
gint8 ber_class;
|
||||
gboolean pc;
|
||||
gint32 tag;
|
||||
guint32 len;
|
||||
int eoffset;
|
||||
int hoffset;
|
||||
const char *str;
|
||||
proto_item *cause;
|
||||
const gchar *name;
|
||||
header_field_info *hfi;
|
||||
|
||||
#ifdef DEBUG_BER
|
||||
{
|
||||
header_field_info *hfinfo;
|
||||
if (hf_id >= 0) {
|
||||
hfinfo = proto_registrar_get_nth(hf_id);
|
||||
name = hfinfo->name;
|
||||
} else {
|
||||
name = "unnamed";
|
||||
}
|
||||
if (tvb_length_remaining(tvb, offset) > 3) {
|
||||
printf("OBJECT IDENTIFIER dissect_ber_relative_oid(%s) entered implicit_tag:%d offset:%d len:%d %02x:%02x:%02x\n", name, implicit_tag, offset, tvb_length_remaining(tvb, offset), tvb_get_guint8(tvb, offset), tvb_get_guint8(tvb, offset+1), tvb_get_guint8(tvb, offset+2));
|
||||
} else {
|
||||
printf("OBJECT IDENTIFIER dissect_ber_relative_oid(%s) entered\n", name);
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
if (!implicit_tag) {
|
||||
hoffset = offset;
|
||||
/* sanity check */
|
||||
offset = dissect_ber_identifier(actx->pinfo, tree, tvb, offset, &ber_class, &pc, &tag);
|
||||
offset = dissect_ber_length(actx->pinfo, tree, tvb, offset, &len, NULL);
|
||||
eoffset = offset + len;
|
||||
if ( (ber_class != BER_CLASS_UNI)
|
||||
|| (tag != BER_UNI_TAG_OID) ) {
|
||||
tvb_ensure_bytes_exist(tvb, hoffset, 2);
|
||||
cause = proto_tree_add_string_format(
|
||||
tree, hf_ber_error, tvb, offset, len, "oid_expected",
|
||||
"BER Error: Object Identifier expected but class:%s(%d) %s tag:%d was unexpected",
|
||||
val_to_str_const(ber_class, ber_class_codes, "Unknown"),
|
||||
ber_class,
|
||||
pc ? ber_pc_codes_short.true_string : ber_pc_codes_short.false_string,
|
||||
tag);
|
||||
expert_add_info(actx->pinfo, cause, &ei_ber_expected_object_identifier);
|
||||
if (decode_unexpected) {
|
||||
proto_tree *unknown_tree = proto_item_add_subtree(cause, ett_ber_unknown);
|
||||
dissect_unknown_ber(actx->pinfo, tvb, hoffset, unknown_tree);
|
||||
}
|
||||
return eoffset;
|
||||
}
|
||||
} else {
|
||||
len = tvb_length_remaining(tvb, offset);
|
||||
eoffset = offset+len;
|
||||
}
|
||||
|
||||
actx->created_item = NULL;
|
||||
hfi = proto_registrar_get_nth(hf_id);
|
||||
if (hfi->type == FT_REL_OID) {
|
||||
actx->created_item = proto_tree_add_item(tree, hf_id, tvb, offset, len, ENC_BIG_ENDIAN);
|
||||
} else if (IS_FT_STRING(hfi->type)) {
|
||||
str = oid_encoded2string(tvb_get_ptr(tvb, offset, len), len);
|
||||
actx->created_item = proto_tree_add_string(tree, hf_id, tvb, offset, len, str);
|
||||
if (actx->created_item) {
|
||||
/* see if we know the name of this oid */
|
||||
name = oid_resolved_from_encoded(tvb_get_ptr(tvb, offset, len), len);
|
||||
if (name) {
|
||||
proto_item_append_text(actx->created_item, " (%s)", name);
|
||||
}
|
||||
}
|
||||
} else {
|
||||
DISSECTOR_ASSERT_NOT_REACHED();
|
||||
}
|
||||
|
||||
if (value_tvb)
|
||||
*value_tvb = tvb_new_subset(tvb, offset, len, len);
|
||||
|
||||
return eoffset;
|
||||
}
|
||||
|
||||
int
|
||||
dissect_ber_relative_oid_str(gboolean implicit_tag, asn1_ctx_t *actx, proto_tree *tree, tvbuff_t *tvb, int offset, gint hf_id, const char **value_stringx)
|
||||
{
|
||||
tvbuff_t *value_tvb = NULL;
|
||||
guint length;
|
||||
|
||||
offset = dissect_ber_object_identifier(implicit_tag, actx, tree, tvb, offset, hf_id, (value_stringx) ? &value_tvb : NULL);
|
||||
|
||||
if (value_stringx) {
|
||||
if (value_tvb && (length = tvb_length(value_tvb))) {
|
||||
*value_stringx = oid_encoded2string(tvb_get_ptr(value_tvb, 0, length), length);
|
||||
} else {
|
||||
*value_stringx = "";
|
||||
}
|
||||
}
|
||||
|
||||
return offset;
|
||||
}
|
||||
|
||||
/* 8.19 Encoding of an object identifier value.
|
||||
*/
|
||||
int
|
||||
|
@ -3851,7 +3950,6 @@ dissect_ber_object_identifier(gboolean implicit_tag, asn1_ctx_t *actx, proto_tre
|
|||
|
||||
#ifdef DEBUG_BER
|
||||
{
|
||||
const char *name;
|
||||
header_field_info *hfinfo;
|
||||
if (hf_id >= 0) {
|
||||
hfinfo = proto_registrar_get_nth(hf_id);
|
||||
|
|
|
@ -195,6 +195,11 @@ extern int dissect_ber_GeneralString(asn1_ctx_t *actx, proto_tree *tree, tvbuff_
|
|||
WS_DLL_PUBLIC int dissect_ber_object_identifier(gboolean implicit_tag, asn1_ctx_t *actx, proto_tree *tree, tvbuff_t *tvb, int offset, gint hf_id, tvbuff_t **value_tvb);
|
||||
WS_DLL_PUBLIC int dissect_ber_object_identifier_str(gboolean implicit_tag, asn1_ctx_t *actx, proto_tree *tree, tvbuff_t *tvb, int offset, gint hf_id, const char **value_stringx);
|
||||
|
||||
/* this function dissects a BER Relative Object Identifier
|
||||
*/
|
||||
WS_DLL_PUBLIC int dissect_ber_relative_oid(gboolean implicit_tag, asn1_ctx_t *actx, proto_tree *tree, tvbuff_t *tvb, int offset, gint hf_id, tvbuff_t **value_tvb);
|
||||
WS_DLL_PUBLIC int dissect_ber_relative_oid_str(gboolean implicit_tag, asn1_ctx_t *actx, proto_tree *tree, tvbuff_t *tvb, int offset, gint hf_id, const char **value_stringx);
|
||||
|
||||
/* this function dissects a BER sequence of
|
||||
*/
|
||||
extern int dissect_ber_constrained_sequence_of(gboolean implicit_tag, asn1_ctx_t *actx, proto_tree *parent_tree, tvbuff_t *tvb, int offset, gint32 min_len, gint32 max_len, const ber_sequence_t *seq, gint hf_id, gint ett_id);
|
||||
|
|
|
@ -77,6 +77,8 @@ bytes_repr_len(fvalue_t *fv, ftrepr_t rtype _U_)
|
|||
* OID_REPR_LEN:
|
||||
*
|
||||
* 5 for the first byte ([0-2].[0-39].)
|
||||
*
|
||||
* REL_OID_REPR_LEN:
|
||||
* for each extra byte if the sub-id is:
|
||||
* 1 byte it can be at most "127." (4 bytes we give it 4)
|
||||
* 2 bytes it can be at most "16383." (6 bytes we give it 8)
|
||||
|
@ -87,7 +89,8 @@ bytes_repr_len(fvalue_t *fv, ftrepr_t rtype _U_)
|
|||
* a 5 bytes encoded subid can already overflow the guint32 that holds a sub-id,
|
||||
* making it a completely different issue!
|
||||
*/
|
||||
#define OID_REPR_LEN(fv) (5 + (4 * ((fv)->value.bytes->len-1)))
|
||||
#define REL_OID_REPR_LEN(fv) (4 * ((fv)->value.bytes->len))
|
||||
#define OID_REPR_LEN(fv) (1 + REL_OID_REPR_LEN(fv))
|
||||
|
||||
static int
|
||||
oid_repr_len(fvalue_t *fv _U_, ftrepr_t rtype _U_)
|
||||
|
@ -109,6 +112,27 @@ oid_to_repr(fvalue_t *fv, ftrepr_t rtype _U_, char *buf)
|
|||
strncpy(buf,oid_str,OID_REPR_LEN(fv));
|
||||
}
|
||||
|
||||
static int
|
||||
rel_oid_repr_len(fvalue_t *fv _U_, ftrepr_t rtype _U_)
|
||||
{
|
||||
return REL_OID_REPR_LEN(fv);
|
||||
}
|
||||
|
||||
static void
|
||||
rel_oid_to_repr(fvalue_t *fv, ftrepr_t rtype _U_, char *buf)
|
||||
{
|
||||
const char* oid_str = rel_oid_encoded2string(fv->value.bytes->data,fv->value.bytes->len);
|
||||
/*
|
||||
* XXX:
|
||||
* I'm assuming that oid_repr_len is going to be called before to set buf's size.
|
||||
* or else we might have a BO.
|
||||
* I guess that is why this callback is not passed a length.
|
||||
* -- lego
|
||||
*/
|
||||
*buf++ = '.';
|
||||
strncpy(buf,oid_str,REL_OID_REPR_LEN(fv));
|
||||
}
|
||||
|
||||
static void
|
||||
bytes_to_repr(fvalue_t *fv, ftrepr_t rtype _U_, char *buf)
|
||||
{
|
||||
|
@ -378,6 +402,34 @@ oid_from_unparsed(fvalue_t *fv, char *s, gboolean allow_partial_value _U_, LogFu
|
|||
return TRUE;
|
||||
}
|
||||
|
||||
static gboolean
|
||||
rel_oid_from_unparsed(fvalue_t *fv, char *s, gboolean allow_partial_value _U_, LogFunc logfunc)
|
||||
{
|
||||
GByteArray *bytes;
|
||||
gboolean res;
|
||||
|
||||
|
||||
/*
|
||||
* Don't log a message if this fails; we'll try looking it
|
||||
* up as an OID if it does, and if that fails,
|
||||
* we'll log a message.
|
||||
*/
|
||||
bytes = g_byte_array_new();
|
||||
res = rel_oid_str_to_bytes(s, bytes, FALSE);
|
||||
if (!res) {
|
||||
if (logfunc != NULL)
|
||||
logfunc("\"%s\" is not a valid RELATIVE-OID.", s);
|
||||
g_byte_array_free(bytes, TRUE);
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
/* Free up the old value, if we have one */
|
||||
bytes_fvalue_free(fv);
|
||||
fv->value.bytes = bytes;
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static guint
|
||||
len(fvalue_t *fv)
|
||||
{
|
||||
|
@ -811,10 +863,49 @@ ftype_register_bytes(void)
|
|||
slice,
|
||||
};
|
||||
|
||||
static ftype_t rel_oid_type = {
|
||||
FT_REL_OID, /* ftype */
|
||||
"FT_REL_OID", /* name */
|
||||
"ASN.1 relative object identifier", /* pretty_name */
|
||||
0, /* wire_size */
|
||||
bytes_fvalue_new, /* new_value */
|
||||
bytes_fvalue_free, /* free_value */
|
||||
rel_oid_from_unparsed, /* val_from_unparsed */
|
||||
NULL, /* val_from_string */
|
||||
rel_oid_to_repr, /* val_to_string_repr */
|
||||
rel_oid_repr_len, /* len_string_repr */
|
||||
|
||||
oid_fvalue_set, /* set_value (same as full oid) */
|
||||
NULL, /* set_value_uinteger */
|
||||
NULL, /* set_value_sinteger */
|
||||
NULL, /* set_value_integer64 */
|
||||
NULL, /* set_value_floating */
|
||||
|
||||
value_get, /* get_value */
|
||||
NULL, /* get_value_uinteger */
|
||||
NULL, /* get_value_sinteger */
|
||||
NULL, /* get_value_integer64 */
|
||||
NULL, /* get_value_floating */
|
||||
|
||||
cmp_eq,
|
||||
cmp_ne,
|
||||
cmp_gt,
|
||||
cmp_ge,
|
||||
cmp_lt,
|
||||
cmp_le,
|
||||
cmp_bitwise_and,
|
||||
cmp_contains,
|
||||
NULL, /* cmp_matches */
|
||||
|
||||
len,
|
||||
slice,
|
||||
};
|
||||
|
||||
ftype_register(FT_BYTES, &bytes_type);
|
||||
ftype_register(FT_UINT_BYTES, &uint_bytes_type);
|
||||
ftype_register(FT_AX25, &ax25_type);
|
||||
ftype_register(FT_VINES, &vines_type);
|
||||
ftype_register(FT_ETHER, ðer_type);
|
||||
ftype_register(FT_OID, &oid_type);
|
||||
ftype_register(FT_REL_OID, &rel_oid_type);
|
||||
}
|
||||
|
|
|
@ -69,6 +69,7 @@ enum ftenum {
|
|||
FT_EUI64,
|
||||
FT_AX25,
|
||||
FT_VINES,
|
||||
FT_REL_OID, /* RELATIVE-OID */
|
||||
FT_NUM_TYPES /* last item number plus one */
|
||||
};
|
||||
|
||||
|
|
30
epan/oids.c
30
epan/oids.c
|
@ -829,11 +829,16 @@ void oids_cleanup(void) {
|
|||
}
|
||||
|
||||
const char* oid_subid2string(guint32* subids, guint len) {
|
||||
return rel_oid_subid2string(subids, len, TRUE);
|
||||
}
|
||||
const char* rel_oid_subid2string(guint32* subids, guint len, gboolean is_absolute) {
|
||||
char* s = (char *)ep_alloc0(((len)*11)+1);
|
||||
char* w = s;
|
||||
|
||||
if(!subids)
|
||||
return "*** Empty OID ***";
|
||||
if (!is_absolute)
|
||||
*w++ = '.';
|
||||
|
||||
do {
|
||||
w += g_snprintf(w,12,"%u.",*subids++);
|
||||
|
@ -919,9 +924,12 @@ guint oid_string2subid(const char* str, guint32** subids_p) {
|
|||
|
||||
|
||||
guint oid_encoded2subid(const guint8 *oid_bytes, gint oid_len, guint32** subids_p) {
|
||||
return oid_encoded2subid_sub(oid_bytes, oid_len, subids_p, TRUE);
|
||||
}
|
||||
guint oid_encoded2subid_sub(const guint8 *oid_bytes, gint oid_len, guint32** subids_p,
|
||||
gboolean is_first) {
|
||||
gint i;
|
||||
guint n = 1;
|
||||
gboolean is_first = TRUE;
|
||||
guint n = is_first ? 1 : 0;
|
||||
guint32* subids;
|
||||
guint32* subid_overflow;
|
||||
/*
|
||||
|
@ -939,7 +947,7 @@ guint oid_encoded2subid(const guint8 *oid_bytes, gint oid_len, guint32** subids_
|
|||
* so initialize our one byte to zero and return. This *seems* to be
|
||||
* the right thing to do in this situation, and at the very least it
|
||||
* avoids uninitialized memory errors that would otherwise occur. */
|
||||
if (n == 1) {
|
||||
if ((is_first && n == 0) || (!is_first && n == 1)) {
|
||||
*subids = 0;
|
||||
return n;
|
||||
}
|
||||
|
@ -1019,6 +1027,13 @@ const gchar *oid_resolved_from_encoded(const guint8 *oid, gint oid_len) {
|
|||
return oid_resolved(subid_oid_length, subid_oid);
|
||||
}
|
||||
|
||||
const gchar *rel_oid_resolved_from_encoded(const guint8 *oid, gint oid_len) {
|
||||
guint32 *subid_oid;
|
||||
guint subid_oid_length = oid_encoded2subid_sub(oid, oid_len, &subid_oid, FALSE);
|
||||
|
||||
return rel_oid_subid2string(subid_oid, subid_oid_length, FALSE);
|
||||
}
|
||||
|
||||
|
||||
guint oid_subid2encoded(guint subids_len, guint32* subids, guint8** bytes_p) {
|
||||
guint bytelen = 0;
|
||||
|
@ -1090,7 +1105,16 @@ const gchar* oid_encoded2string(const guint8* encoded, guint len) {
|
|||
}
|
||||
}
|
||||
|
||||
const gchar* rel_oid_encoded2string(const guint8* encoded, guint len) {
|
||||
guint32* subids;
|
||||
guint subids_len = oid_encoded2subid_sub(encoded, len, &subids, FALSE);
|
||||
|
||||
if (subids_len) {
|
||||
return rel_oid_subid2string(subids,subids_len, FALSE);
|
||||
} else {
|
||||
return "";
|
||||
}
|
||||
}
|
||||
|
||||
guint oid_string2encoded(const char *oid_str, guint8 **bytes) {
|
||||
guint32* subids;
|
||||
|
|
|
@ -142,14 +142,20 @@ guint oid_string2encoded(const gchar *oid_str, guint8** encoded_p);
|
|||
WS_DLL_PUBLIC
|
||||
guint oid_encoded2subid(const guint8 *oid, gint len, guint32** subids_p);
|
||||
WS_DLL_PUBLIC
|
||||
guint oid_encoded2subid_sub(const guint8 *oid_bytes, gint oid_len, guint32** subids_pi,
|
||||
gboolean is_first);
|
||||
WS_DLL_PUBLIC
|
||||
guint oid_string2subid(const gchar *oid_str, guint32** subids_p);
|
||||
|
||||
WS_DLL_PUBLIC const gchar* oid_encoded2string(const guint8* encoded, guint len);
|
||||
WS_DLL_PUBLIC const gchar* rel_oid_encoded2string(const guint8* encoded, guint len);
|
||||
WS_DLL_PUBLIC const gchar* oid_subid2string(guint32 *subids, guint len);
|
||||
WS_DLL_PUBLIC const gchar* rel_oid_subid2string(guint32 *subids, guint len, gboolean is_relative);
|
||||
|
||||
/* these return a formated string as human readable as posible */
|
||||
WS_DLL_PUBLIC const gchar *oid_resolved(guint len, guint32 *subids);
|
||||
WS_DLL_PUBLIC const gchar *oid_resolved_from_encoded(const guint8 *oid, gint len);
|
||||
WS_DLL_PUBLIC const gchar *rel_oid_resolved_from_encoded(const guint8 *oid, gint len);
|
||||
WS_DLL_PUBLIC const gchar *oid_resolved_from_string(const gchar *oid_str);
|
||||
|
||||
/* these yield two formated strings one resolved and one numeric */
|
||||
|
|
27
epan/proto.c
27
epan/proto.c
|
@ -1406,6 +1406,7 @@ proto_tree_new_item(field_info *new_fi, proto_tree *tree,
|
|||
break;
|
||||
|
||||
case FT_OID:
|
||||
case FT_REL_OID:
|
||||
proto_tree_set_oid_tvb(new_fi, tvb, start, length);
|
||||
break;
|
||||
|
||||
|
@ -3876,6 +3877,17 @@ proto_custom_set(proto_tree* tree, const int field_id, gint occurrence,
|
|||
size-offset_r);
|
||||
break;
|
||||
|
||||
case FT_REL_OID:
|
||||
bytes = (guint8 *)fvalue_get(&finfo->value);
|
||||
offset_r += protoo_strlcpy(result+offset_r,
|
||||
rel_oid_resolved_from_encoded(bytes,
|
||||
fvalue_length(&finfo->value)),
|
||||
size-offset_r);
|
||||
offset_e += protoo_strlcpy(expr+offset_e,
|
||||
rel_oid_encoded2string(bytes, fvalue_length(&finfo->value)),
|
||||
size-offset_e);
|
||||
break;
|
||||
|
||||
case FT_OID:
|
||||
bytes = (guint8 *)fvalue_get(&finfo->value);
|
||||
offset_r += protoo_strlcpy(result+offset_r,
|
||||
|
@ -3933,6 +3945,7 @@ proto_custom_set(proto_tree* tree, const int field_id, gint occurrence,
|
|||
case FT_INT24:
|
||||
case FT_INT32:
|
||||
case FT_OID:
|
||||
case FT_REL_OID:
|
||||
/* for these types, "expr" is filled in the loop above */
|
||||
break;
|
||||
|
||||
|
@ -4785,6 +4798,7 @@ static const value_string hf_types[] = {
|
|||
{ FT_PCRE, "FT_PCR" },
|
||||
{ FT_GUID, "FT_GUID" },
|
||||
{ FT_OID, "FT_OID" },
|
||||
{ FT_REL_OID, "FT_REL_OID" },
|
||||
{ 0, NULL } };
|
||||
|
||||
static const value_string hf_display[] = {
|
||||
|
@ -5385,6 +5399,19 @@ proto_item_fill_label(field_info *fi, gchar *label_str)
|
|||
oid_encoded2string(bytes, fvalue_length(&fi->value)));
|
||||
}
|
||||
break;
|
||||
|
||||
case FT_REL_OID:
|
||||
bytes = (guint8 *)fvalue_get(&fi->value);
|
||||
name = rel_oid_resolved_from_encoded(bytes, fvalue_length(&fi->value));
|
||||
if (name) {
|
||||
label_fill_descr(label_str, 0, hfinfo,
|
||||
rel_oid_encoded2string(bytes, fvalue_length(&fi->value)), name);
|
||||
} else {
|
||||
label_fill(label_str, 0, hfinfo,
|
||||
rel_oid_encoded2string(bytes, fvalue_length(&fi->value)));
|
||||
}
|
||||
break;
|
||||
|
||||
case FT_EUI64:
|
||||
integer64 = fvalue_get_integer64(&fi->value);
|
||||
label_fill_descr(label_str, 0, hfinfo,
|
||||
|
|
|
@ -617,6 +617,10 @@ byte_array_dup(GByteArray *ba) {
|
|||
#define SUBID_BUF_LEN 5
|
||||
gboolean
|
||||
oid_str_to_bytes(const char *oid_str, GByteArray *bytes) {
|
||||
return rel_oid_str_to_bytes(oid_str, bytes, TRUE);
|
||||
}
|
||||
gboolean
|
||||
rel_oid_str_to_bytes(const char *oid_str, GByteArray *bytes, gboolean is_absolute) {
|
||||
guint32 subid0, subid, sicnt, i;
|
||||
const char *p, *dot;
|
||||
guint8 buf[SUBID_BUF_LEN];
|
||||
|
@ -629,7 +633,7 @@ oid_str_to_bytes(const char *oid_str, GByteArray *bytes) {
|
|||
while (*p) {
|
||||
if (!isdigit((guchar)*p) && (*p != '.')) return FALSE;
|
||||
if (*p == '.') {
|
||||
if (p == oid_str) return FALSE;
|
||||
if (p == oid_str && is_absolute) return FALSE;
|
||||
if (!*(p+1)) return FALSE;
|
||||
if ((p-1) == dot) return FALSE;
|
||||
dot = p;
|
||||
|
@ -639,7 +643,8 @@ oid_str_to_bytes(const char *oid_str, GByteArray *bytes) {
|
|||
if (!dot) return FALSE;
|
||||
|
||||
p = oid_str;
|
||||
sicnt = 0;
|
||||
sicnt = is_absolute ? 0 : 2;
|
||||
if (!is_absolute) p++;
|
||||
subid0 = 0; /* squelch GCC complaints */
|
||||
while (*p) {
|
||||
subid = 0;
|
||||
|
|
|
@ -151,6 +151,17 @@ gboolean uri_str_to_bytes(const char *uri_str, GByteArray *bytes);
|
|||
WS_DLL_PUBLIC
|
||||
const gchar* format_uri(const GByteArray *bytes, const gchar *reserved_chars);
|
||||
|
||||
/** Turn a OID string representation (dot notation) into a byte array.
|
||||
*
|
||||
* @param oid_str The OID string (dot notaion).
|
||||
* @param bytes The GByteArray that will receive the bytes. This
|
||||
* must be initialized by the caller.
|
||||
* @param is_absolute True if this is an absolute OID; false for relative OID.
|
||||
* @return True if the string was converted successfully
|
||||
*/
|
||||
WS_DLL_PUBLIC
|
||||
gboolean rel_oid_str_to_bytes(const char *oid_str, GByteArray *bytes, gboolean is_absolute);
|
||||
|
||||
/** Turn a OID string representation (dot notation) into a byte array.
|
||||
*
|
||||
* @param oid_str The OID string (dot notaion).
|
||||
|
|
|
@ -155,6 +155,7 @@ WSLUA_METAMETHOD FieldInfo__call(lua_State* L) {
|
|||
case FT_UINT_BYTES:
|
||||
case FT_GUID:
|
||||
case FT_PROTOCOL:
|
||||
case FT_REL_OID:
|
||||
case FT_OID: {
|
||||
ByteArray ba = g_byte_array_new();
|
||||
g_byte_array_append(ba, (const guint8 *)tvb_memdup(wmem_packet_scope(),fi->ds_tvb,fi->start,fi->length),fi->length);
|
||||
|
|
|
@ -459,6 +459,7 @@ static const wslua_ft_types_t ftenums[] = {
|
|||
{"ftypes.FRAMENUM", FT_FRAMENUM},
|
||||
{"ftypes.GUID", FT_GUID},
|
||||
{"ftypes.OID", FT_OID},
|
||||
{"ftypes.REL_OID", FT_REL_OID},
|
||||
{NULL, FT_NONE}
|
||||
};
|
||||
|
||||
|
@ -1185,6 +1186,7 @@ PROTOFIELD_OTHER(bytes,FT_BYTES)
|
|||
PROTOFIELD_OTHER(ubytes,FT_UINT_BYTES)
|
||||
PROTOFIELD_OTHER(guid,FT_GUID)
|
||||
PROTOFIELD_OTHER(oid,FT_OID)
|
||||
PROTOFIELD_OTHER(rel_oid,FT_REL_OID)
|
||||
|
||||
WSLUA_METAMETHOD ProtoField__tostring(lua_State* L) {
|
||||
/* Returns a string with info about a protofield (for debugging purposes) */
|
||||
|
@ -1246,6 +1248,7 @@ static const luaL_Reg ProtoField_methods[] = {
|
|||
{"ubytes",ProtoField_ubytes},
|
||||
{"guid",ProtoField_guid},
|
||||
{"oid",ProtoField_oid},
|
||||
{"rel_oid",ProtoField_rel_oid},
|
||||
{ NULL, NULL }
|
||||
};
|
||||
|
||||
|
|
|
@ -225,6 +225,7 @@ static int TreeItem_add_item_any(lua_State *L, gboolean little_endian) {
|
|||
case FT_IPXNET:
|
||||
case FT_GUID:
|
||||
case FT_OID:
|
||||
case FT_REL_OID:
|
||||
default:
|
||||
luaL_error(L,"FT_ not yet supported");
|
||||
return 0;
|
||||
|
|
|
@ -66,7 +66,8 @@ FT_IPXNET,
|
|||
FT_FRAMENUM,
|
||||
FT_PCRE,
|
||||
FT_GUID,
|
||||
FT_OID) = map(int, range(31))
|
||||
FT_OID,
|
||||
FT_REL_OID) = map(int, range(32))
|
||||
|
||||
# hf_register_info from usual dissectors
|
||||
class register_info(object):
|
||||
|
|
|
@ -1239,6 +1239,8 @@ static const char* ftenum_to_string(header_field_info *hfi)
|
|||
return "FT_GUID";
|
||||
case FT_OID:
|
||||
return "FT_OID";
|
||||
case FT_REL_OID:
|
||||
return "FT_REL_OID";
|
||||
case FT_NUM_TYPES:
|
||||
return "FT_NUM_TYPES";
|
||||
default:
|
||||
|
|
|
@ -5301,7 +5301,7 @@ class RelativeOIDType (Type):
|
|||
return 'RELATIVE_OID'
|
||||
|
||||
def eth_ftype(self, ectx):
|
||||
return ('FT_BYTES', 'BASE_NONE')
|
||||
return ('FT_REL_OID', 'BASE_NONE')
|
||||
|
||||
def GetTTag(self, ectx):
|
||||
return ('BER_CLASS_UNI', 'BER_UNI_TAG_RELATIVE_OID')
|
||||
|
|
|
@ -86,7 +86,7 @@ my %FIELD_TYPE = ('FT_NONE' => "FT_NONE", 'FT_PROTOCOL' => "FT_PROTOCOL", 'FT_BO
|
|||
'FT_STRING' => "FT_STRING", 'FT_STRINGZ' => "FT_STRINGZ", 'FT_UINT_STRING' => "FT_UINT_STRING",
|
||||
'FT_ETHER' => "FT_ETHER", 'FT_BYTES' => "FT_BYTES", 'FT_UINT_BYTES' => "FT_UINT_BYTES",
|
||||
'FT_IPv4' => "FT_IPv4", 'FT_IPv6' => "FT_IPv6", 'FT_IPXNET' => "FT_IPXNET", 'FT_AX25' => "FT_AX25", 'FT_VINES' => "FT_VINES",
|
||||
'FT_FRAMENUM' => "FT_FRAMENUM", 'FT_PCRE' => "FT_PCRE", 'FT_GUID' => "FT_GUID", 'FT_OID' => "FT_OID", 'FT_EUI64' => "FT_EUI64");
|
||||
'FT_FRAMENUM' => "FT_FRAMENUM", 'FT_PCRE' => "FT_PCRE", 'FT_GUID' => "FT_GUID", 'FT_OID' => "FT_OID", 'FT_REL_OID' => "FT_REL_OID", 'FT_EUI64' => "FT_EUI64");
|
||||
|
||||
my %EXPERT_SEVERITY = ('PI_COMMENT' => "PI_COMMENT",
|
||||
'PI_CHAT' => "PI_CHAT",
|
||||
|
|
|
@ -76,7 +76,7 @@ my $searchReplaceEncNAHRef =
|
|||
|
||||
my @types_NA =
|
||||
(
|
||||
[ qw (FT_NONE FT_BYTES FT_ETHER FT_IPv6 FT_IPXNET FT_OID)],
|
||||
[ qw (FT_NONE FT_BYTES FT_ETHER FT_IPv6 FT_IPXNET FT_OID FT_REL_OID)],
|
||||
$searchReplaceEncNAHRef
|
||||
);
|
||||
|
||||
|
@ -179,6 +179,7 @@ my @types_ALL =
|
|||
FT_PCRE
|
||||
FT_GUID
|
||||
FT_OID
|
||||
FT_REL_OID
|
||||
FT_EUI64
|
||||
)],
|
||||
{# valid encoding args
|
||||
|
|
|
@ -92,7 +92,7 @@ resolve_column (gint col, capture_file *cf)
|
|||
/* Check if this is a valid field */
|
||||
if (hfi != NULL) {
|
||||
/* Check if we have an OID or a strings table with integer values */
|
||||
if ((hfi->type == FT_OID) ||
|
||||
if ((hfi->type == FT_OID) || (hfi->type == FT_REL_OID) ||
|
||||
((hfi->strings != NULL) &&
|
||||
((hfi->type == FT_BOOLEAN) || (hfi->type == FT_FRAMENUM) ||
|
||||
IS_FT_INT(hfi->type) || IS_FT_UINT(hfi->type)))) {
|
||||
|
|
Loading…
Reference in New Issue