Skip to content

Commit

Permalink
Runtime tests: Allow multiline PROGs and EXPECTs
Browse files Browse the repository at this point in the history
The previous options had some downsides:
- Define the program/expected results in an external file:
    Out-of-line definitions add barriers to quickly understanding tests and to
    adding new tests
- Use EXPECT_REGEX:
    Hard to read due to escape characters and being squashed onto a single line
- Use multiple EXPECTs:
    Do not enforce ordering of output lines
  • Loading branch information
ajor committed Apr 16, 2024
1 parent 45b8c8c commit 5eed629
Show file tree
Hide file tree
Showing 4 changed files with 42 additions and 14 deletions.
14 changes: 12 additions & 2 deletions tests/runtime/call
Expand Up @@ -412,12 +412,22 @@ TIMEOUT 1

NAME print_avg_map_args
PROG BEGIN { print("BEGIN"); @["a"] = avg(10); @["b"] = avg(20); @["c"] = avg(30); @["d"] = avg(40); print(@, 2, 10); print("END"); clear(@); exit(); }
EXPECT_REGEX BEGIN\n@\[c\]: 3\n@\[d\]: 4\n\nEND
EXPECT BEGIN
@[c]: 3
@[d]: 4

END
TIMEOUT 1

NAME print_avg_map_with_large_top
PROG BEGIN { print("BEGIN"); @["a"] = avg(10); @["b"] = avg(20); @["c"] = avg(30); @["d"] = avg(40); print(@, 10, 10); print("END"); clear(@); exit(); }
EXPECT_REGEX BEGIN\n@\[a\]: 1\n@\[b\]: 2\n@\[c\]: 3\n@\[d\]: 4\n\nEND
EXPECT BEGIN
@[a]: 1
@[b]: 2
@[c]: 3
@[d]: 4

END
TIMEOUT 1

NAME print_hist_with_top_arg
Expand Down
15 changes: 15 additions & 0 deletions tests/runtime/engine/parser.py
Expand Up @@ -123,11 +123,26 @@ def __read_test_struct(test, test_suite):
will_fail = False
new_pidns = False
skip_if_env_has = None
prev_item_name = ''

for item in test:
if item[:len(prev_item_name) + 1].isspace():
# Whitespace at beginning of line means it continues from the
# previous line

# Remove the leading whitespace and the trailing newline
line = item[len(prev_item_name) + 1:-1]
if prev_item_name == 'PROG':
prog += '\n' + line
continue
elif prev_item_name == 'EXPECT':
expects[-1].expect += '\n' + line
continue

item_split = item.split()
item_name = item_split[0]
line = ' '.join(item_split[1:])
prev_item_name = item_name

if item_name == 'NAME':
name = line
Expand Down
20 changes: 10 additions & 10 deletions tests/runtime/other
Expand Up @@ -61,16 +61,16 @@ TIMEOUT 5
NAME unroll_max_value
PROG i:ms:1 {$a = 1; unroll (101) { $a = $a + 2; } printf("a=%d\n", $a); exit();}
EXPECT stdin:1:17-29: ERROR: unroll maximum value is 100
EXPECT i:ms:1 {$a = 1; unroll (101) { $a = $a + 2; } printf("a=%d\n", $a); exit();}
EXPECT ~~~~~~~~~~~~
i:ms:1 {$a = 1; unroll (101) { $a = $a + 2; } printf("a=%d\n", $a); exit();}
~~~~~~~~~~~~
TIMEOUT 5
WILL_FAIL

NAME unroll_min_value
PROG i:ms:1 {$a = 1; unroll (0) { $a = $a + 2; } printf("a=%d\n", $a); exit();}
EXPECT stdin:1:17-27: ERROR: unroll minimum value is 1
EXPECT i:ms:1 {$a = 1; unroll (0) { $a = $a + 2; } printf("a=%d\n", $a); exit();}
EXPECT ~~~~~~~~~~
i:ms:1 {$a = 1; unroll (0) { $a = $a + 2; } printf("a=%d\n", $a); exit();}
~~~~~~~~~~
TIMEOUT 5
WILL_FAIL

Expand Down Expand Up @@ -267,15 +267,15 @@ TIMEOUT 1
NAME runtime_error_check_delete
RUN {{BPFTRACE}} -k -e 'i:ms:100 { @[1] = 1; delete(@[2]); exit(); }'
EXPECT stdin:1:22-34: WARNING: Can't delete map element because it does not exist.
EXPECT Additional Info - helper: map_delete_elem, retcode: -2
EXPECT i:ms:100 { @[1] = 1; delete(@[2]); exit(); }
EXPECT ~~~~~~~~~~~~
Additional Info - helper: map_delete_elem, retcode: -2
i:ms:100 { @[1] = 1; delete(@[2]); exit(); }
~~~~~~~~~~~~
TIMEOUT 1

NAME runtime_error_check_lookup
RUN {{BPFTRACE}} -kk -e 'i:ms:100 { @[1] = 1; printf("%d\n", @[2]); exit(); }'
EXPECT stdin:1:37-41: WARNING: Can't lookup map element because it does not exist.
EXPECT Additional Info - helper: map_lookup_elem, retcode: 0
EXPECT i:ms:100 { @[1] = 1; printf("%d\n", @[2]); exit(); }
EXPECT ~~~~
Additional Info - helper: map_lookup_elem, retcode: 0
i:ms:100 { @[1] = 1; printf("%d\n", @[2]); exit(); }
~~~~
TIMEOUT 1
7 changes: 5 additions & 2 deletions tests/runtime/probe
Expand Up @@ -36,7 +36,9 @@ AFTER ./testprogs/syscall read
# https://github.com/bpftrace/bpftrace/issues/2447
NAME kfunc_multiple_attach_point_multiple_functions
PROG BEGIN { @a = 2; @b = 1; @c = 1 } i:s:1 { exit() } kfunc:vfs_read, kfunc:vfs_open /@a != 0/ { @a -= 1 } kfunc:vfs_read /@b == 1/ { @b = 0 } kfunc:vfs_open /@c == 1/ { @c = 0 }
EXPECT_REGEX @a: 0\n@b: 0\n@c: 0
EXPECT @a: 0
@b: 0
@c: 0
TIMEOUT 5
REQUIRES_FEATURE kfunc
# Note: this calls both vfs_read and vfs_open
Expand Down Expand Up @@ -476,7 +478,8 @@ TIMEOUT 2

NAME BEGIN,END
PROG BEGIN,END { printf("Hello\n"); exit(); }
EXPECT_REGEX Hello\nHello
EXPECT Hello
Hello
TIMEOUT 2

# The "probe" builtin forces bpftrace to generate one BPF function for each
Expand Down

0 comments on commit 5eed629

Please sign in to comment.