aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorJoão Valverde <j@v6e.pt>2023-10-31 13:27:23 +0000
committerJoão Valverde <j@v6e.pt>2023-10-31 14:54:19 +0000
commit9b62ec029eb6af5301088c6d8b65f8cf9cf83021 (patch)
tree2723269dcd79c30d2e3ae46b9facf39bf3b7f814
parent1dd58a0559ed009f473f0582d26c1c0bbf194563 (diff)
dfilter: Fix slices with byte references
Before: Filter: frame[:2] == $@frame[:2] Error: Range is not supported for entity @frame <FT_BYTES> frame[:2] == $@frame[:2] ^~~~~~~ After: Filter: frame[:2] == $@frame[:2] Instructions: 0000 READ_TREE frame -> R0 0001 IF_FALSE_GOTO 7 0002 SLICE R0[0:2] -> R1 0003 READ_REFERENCE ${@frame} -> R2 0004 IF_FALSE_GOTO 7 0005 SLICE R2[0:2] -> R3 0006 ANY_EQ R1 == R3 0007 RETURN
-rw-r--r--epan/dfilter/semcheck.c64
-rw-r--r--test/suite_dfilter/group_syntax.py10
2 files changed, 54 insertions, 20 deletions
diff --git a/epan/dfilter/semcheck.c b/epan/dfilter/semcheck.c
index 64ac703993..3c538d56f2 100644
--- a/epan/dfilter/semcheck.c
+++ b/epan/dfilter/semcheck.c
@@ -779,34 +779,58 @@ check_slice(dfwork_t *dfw, stnode_t *st, ftenum_t logical_ftype)
{
stnode_t *entity1;
header_field_info *hfinfo1;
- ftenum_t ftype1;
+ sttype_id_t sttype1;
+ ftenum_t ftype1 = FT_NONE;
LOG_NODE(st);
entity1 = sttype_slice_entity(st);
ws_assert(entity1);
+ sttype1 = stnode_type_id(entity1);
- if (stnode_type_id(entity1) == STTYPE_FIELD) {
- dfw->field_count++;
- hfinfo1 = sttype_field_hfinfo(entity1);
- ftype1 = sttype_field_ftenum(entity1);
+ switch (sttype1) {
+ case STTYPE_FIELD:
+ dfw->field_count++;
+ /* fall-through */
+ case STTYPE_REFERENCE:
+ hfinfo1 = sttype_field_hfinfo(entity1);
+ ftype1 = sttype_field_ftenum(entity1);
- if (!ftype_can_slice(ftype1)) {
- FAIL(dfw, entity1, "\"%s\" is a %s and cannot be sliced into a sequence of bytes.",
- hfinfo1->abbrev, ftype_pretty_name(ftype1));
- }
- } else if (stnode_type_id(entity1) == STTYPE_FUNCTION) {
- ftype1 = check_function(dfw, entity1, logical_ftype);
+ if (!ftype_can_slice(ftype1)) {
+ FAIL(dfw, entity1, "\"%s\" is a %s and cannot be sliced into a sequence of bytes.",
+ hfinfo1->abbrev, ftype_pretty_name(ftype1));
+ }
+ break;
+
+ case STTYPE_FUNCTION:
+ ftype1 = check_function(dfw, entity1, logical_ftype);
+
+ if (!ftype_can_slice(ftype1)) {
+ FAIL(dfw, entity1, "Return value of function \"%s\" is a %s and cannot be converted into a sequence of bytes.",
+ sttype_function_name(entity1), ftype_pretty_name(ftype1));
+ }
+ break;
+
+ case STTYPE_SLICE:
+ ftype1 = check_slice(dfw, entity1, logical_ftype);
+ break;
+
+ case STTYPE_LITERAL:
+ case STTYPE_STRING:
+ case STTYPE_CHARCONST:
+ case STTYPE_NUMBER:
+ FAIL(dfw, entity1, "Range is not supported for entity %s",
+ stnode_todisplay(entity1));
+
+ case STTYPE_UNINITIALIZED:
+ case STTYPE_NUM_TYPES:
+ case STTYPE_PCRE:
+ case STTYPE_FVALUE:
+ case STTYPE_TEST:
+ case STTYPE_ARITHMETIC:
+ case STTYPE_SET:
+ ASSERT_STTYPE_NOT_REACHED(sttype1);
- if (!ftype_can_slice(ftype1)) {
- FAIL(dfw, entity1, "Return value of function \"%s\" is a %s and cannot be converted into a sequence of bytes.",
- sttype_function_name(entity1), ftype_pretty_name(ftype1));
- }
- } else if (stnode_type_id(entity1) == STTYPE_SLICE) {
- ftype1 = check_slice(dfw, entity1, logical_ftype);
- } else {
- FAIL(dfw, entity1, "Range is not supported for entity %s",
- stnode_todisplay(entity1));
}
return FT_IS_STRING(ftype1) ? FT_STRING : FT_BYTES;
diff --git a/test/suite_dfilter/group_syntax.py b/test/suite_dfilter/group_syntax.py
index 89fc5596c1..24e239605c 100644
--- a/test/suite_dfilter/group_syntax.py
+++ b/test/suite_dfilter/group_syntax.py
@@ -353,6 +353,16 @@ class TestDfilterFieldReference:
# select frame 1, expect 1 frames out of 2.
checkDFilterCountWithSelectedFrame(dfilter, 1, 1)
+ def test_ref_5(self, checkDFilterCountWithSelectedFrame):
+ dfilter = 'frame[52-54] == ${@ip.src}[0-2]'
+ # select frame 1, expect 1 frames out of 2.
+ checkDFilterCountWithSelectedFrame(dfilter, 1, 1)
+
+ def test_ref_6(self, checkDFilterCountWithSelectedFrame):
+ dfilter = 'frame[52-54] == $@ip.src[0-2]'
+ # select frame 1, expect 1 frames out of 2.
+ checkDFilterCountWithSelectedFrame(dfilter, 1, 1)
+
class TestDfilterLayer:
trace_file = "ipoipoip.pcap"