PROFINET IO: define an arbitrary recursion depth limit

Bug: 13811
Change-Id: I52bffd4a79dcdad9da23f33e1fc6a868472390bf
Reviewed-on: https://code.wireshark.org/review/22232
Petri-Dish: Pascal Quantin <pascal.quantin@gmail.com>
Tested-by: Petri Dish Buildbot <buildbot-no-reply@wireshark.org>
Reviewed-by: Anders Broman <a.broman58@gmail.com>
This commit is contained in:
Pascal Quantin 2017-06-19 20:06:06 +02:00 committed by Anders Broman
parent 051921854d
commit fbfb87a243
1 changed files with 12 additions and 3 deletions

View File

@ -847,6 +847,7 @@ static expert_field ei_pn_io_ar_info_not_found = EI_INIT;
static expert_field ei_pn_io_iocr_type = EI_INIT;
static expert_field ei_pn_io_frame_id = EI_INIT;
static expert_field ei_pn_io_nr_of_tx_port_groups = EI_INIT;
static expert_field ei_pn_io_max_recursion_depth_reached = EI_INIT;
static e_guid_t uuid_pn_io_device = { 0xDEA00001, 0x6C97, 0x11D1, { 0x82, 0x71, 0x00, 0xA0, 0x24, 0x42, 0xDF, 0x7D } };
static guint16 ver_pn_io_device = 1;
@ -11413,14 +11414,20 @@ dissect_RecordDataWrite(tvbuff_t *tvb, int offset,
return offset;
}
#define PN_IO_MAX_RECURSION_DEPTH 100
static int
dissect_IODWriteReq(tvbuff_t *tvb, int offset,
packet_info *pinfo, proto_tree *tree, guint8 *drep, pnio_ar_t **ar)
packet_info *pinfo, proto_tree *tree, guint8 *drep, pnio_ar_t **ar, guint recursion_count)
{
guint16 u16Index = 0;
guint32 u32RecDataLen = 0;
if (++recursion_count >= PN_IO_MAX_RECURSION_DEPTH) {
proto_tree_add_expert(tree, pinfo, &ei_pn_io_max_recursion_depth_reached,
tvb, 0, 0);
return tvb_captured_length(tvb);
}
/* IODWriteHeader */
offset = dissect_block(tvb, offset, pinfo, tree, drep, &u16Index, &u32RecDataLen, ar);
@ -11428,7 +11435,7 @@ dissect_IODWriteReq(tvbuff_t *tvb, int offset,
/* IODWriteMultipleReq? */
if (u16Index == 0xe040) {
while (tvb_captured_length_remaining(tvb, offset) > 0) {
offset = dissect_IODWriteReq(tvb, offset, pinfo, tree, drep, ar);
offset = dissect_IODWriteReq(tvb, offset, pinfo, tree, drep, ar, recursion_count++);
}
} else {
tvbuff_t *new_tvb = tvb_new_subset_length(tvb, offset, u32RecDataLen);
@ -11460,10 +11467,11 @@ dissect_IPNIO_Write_rqst(tvbuff_t *tvb, int offset,
packet_info *pinfo, proto_tree *tree, dcerpc_info *di, guint8 *drep)
{
pnio_ar_t *ar = NULL;
guint recursion_count = 0;
offset = dissect_IPNIO_rqst_header(tvb, offset, pinfo, tree, di, drep);
offset = dissect_IODWriteReq(tvb, offset, pinfo, tree, drep, &ar);
offset = dissect_IODWriteReq(tvb, offset, pinfo, tree, drep, &ar, recursion_count);
if (ar != NULL) {
pnio_ar_info(tvb, pinfo, tree, ar);
@ -14822,6 +14830,7 @@ proto_register_pn_io (void)
{ &ei_pn_io_iocr_type, { "pn_io.iocr_type.unknown", PI_UNDECODED, PI_WARN, "IOCRType undecoded!", EXPFILL }},
{ &ei_pn_io_localalarmref, { "pn_io.localalarmref.changed", PI_UNDECODED, PI_WARN, "AlarmCRBlockReq: local alarm ref changed", EXPFILL }},
{ &ei_pn_io_nr_of_tx_port_groups, { "pn_io.nr_of_tx_port_groups.not_allowed", PI_PROTOCOL, PI_WARN, "Not allowed value of NumberOfTxPortGroups", EXPFILL }},
{ &ei_pn_io_max_recursion_depth_reached, { "pn_io.max_recursion_depth_reached", PI_PROTOCOL, PI_WARN, "Maximum allowed recursion depth reached - stopping dissection", EXPFILL }}
};
module_t *pnio_module;