aboutsummaryrefslogtreecommitdiffstats
path: root/epan/proto.c
diff options
context:
space:
mode:
authorGerald Combs <gerald@wireshark.org>2016-04-11 15:38:14 -0700
committerGerald Combs <gerald@wireshark.org>2016-04-13 18:46:26 +0000
commit8dc9551e1d56290e6f7f02cc38b77e1d211fd4a5 (patch)
tree4096123e80815883d17c9fafd45ae8d81ae02f53 /epan/proto.c
parent21f1cec9c8c85b75fcb94d793062b5d1a8ed9a9e (diff)
Restrict the depth of the protocol tree.
Limit the the protocol tree to 500 levels. This keeps us from running out of stack space in proto_tree_traverse_{pre,post}_order. Bug: 12268 Change-Id: I60f6b4487bf51a4d43da0429819a8a20fbdb313a Reviewed-on: https://code.wireshark.org/review/14887 Petri-Dish: Gerald Combs <gerald@wireshark.org> Tested-by: Petri Dish Buildbot <buildbot-no-reply@wireshark.org> Reviewed-by: Gerald Combs <gerald@wireshark.org>
Diffstat (limited to 'epan/proto.c')
-rw-r--r--epan/proto.c25
1 files changed, 23 insertions, 2 deletions
diff --git a/epan/proto.c b/epan/proto.c
index c299544476..61ca5d2237 100644
--- a/epan/proto.c
+++ b/epan/proto.c
@@ -56,11 +56,14 @@
#include <wsutil/plugins.h>
+/* Ptvcursor limits */
#define SUBTREE_ONCE_ALLOCATION_NUMBER 8
#define SUBTREE_MAX_LEVELS 256
-/* Throw an exception if we exceed this many tree items. */
-/* XXX - This should probably be a preference */
+
+/* Throw an exception if our tree exceeds these. */
+/* XXX - These should probably be preferences */
#define MAX_TREE_ITEMS (1 * 1000 * 1000)
+#define MAX_TREE_LEVELS (5 * 100)
typedef struct __subtree_lvl {
gint cursor_offset;
@@ -4375,6 +4378,24 @@ proto_tree_add_node(proto_tree *tree, field_info *fi)
{
proto_node *pnode, *tnode, *sibling;
field_info *tfi;
+ int depth = 1;
+
+ /*
+ * Restrict our depth. proto_tree_traverse_pre_order and
+ * proto_tree_traverse_post_order (and possibly others) are recursive
+ * so we need to be mindful of our stack size.
+ */
+ if (tree->first_child == NULL) {
+ for (tnode = tree; tnode != NULL; tnode = tnode->parent) {
+ depth++;
+ if (G_UNLIKELY(depth > MAX_TREE_LEVELS)) {
+ THROW_MESSAGE(DissectorError, wmem_strdup_printf(wmem_packet_scope(),
+ "Maximum tree depth %d exceeded for \"%s\" - \"%s\" (%s:%u)",
+ MAX_TREE_LEVELS,
+ fi->hfinfo->name, fi->hfinfo->abbrev, G_STRFUNC, __LINE__));
+ }
+ }
+ }
/*
* Make sure "tree" is ready to have subtrees under it, by