Skip to content

Commit d0d6748

Browse files
Add --cover-failed-assertions option
This adds an option `--cover-failed-assertions` that prevents the default behaviour of coverage stopping at failed assertions by turning assertions into skips rather than assumes (which is the default behaviour for coverage criteria other than `assertion`, which behaves the same with or without the flag).
1 parent cefd3ce commit d0d6748

File tree

5 files changed

+63
-10
lines changed

5 files changed

+63
-10
lines changed
Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,11 @@
1+
CORE
2+
test.c
3+
--cover location --pointer-check --malloc-may-fail --malloc-fail-null
4+
\[main.coverage.4\] file test.c line \d+ function main block 4 \(lines test.c:main:12,13\): SATISFIED
5+
\[main.coverage.3\] file test.c line \d+ function main block 3 \(lines test.c:main:10\): FAILED
6+
\[main.coverage.2\] file test.c line \d+ function main block 2 \(lines test.c:main:4,5,7,9\): SATISFIED
7+
\[main.coverage.1\] file test.c line \d+ function main block 1 \(lines test.c:main:4\): SATISFIED
8+
^EXIT=0$
9+
^SIGNAL=0$
10+
--
11+
^warning: ignoring
Lines changed: 13 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,13 @@
1+
#include <stdlib.h>
2+
3+
int main() {
4+
int *ptr = malloc(sizeof(*ptr));
5+
int a;
6+
7+
a = *ptr;
8+
9+
if (ptr == NULL)
10+
a = 1;
11+
12+
return 0;
13+
}
Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,11 @@
1+
CORE
2+
test.c
3+
--cover location --cover-failed-assertions --pointer-check --malloc-may-fail --malloc-fail-null
4+
\[main.coverage.4\] file test.c line \d+ function main block 4 \(lines test.c:main:12,13\): SATISFIED
5+
\[main.coverage.3\] file test.c line \d+ function main block 3 \(lines test.c:main:10\): SATISFIED
6+
\[main.coverage.2\] file test.c line \d+ function main block 2 \(lines test.c:main:4,5,7,9\): SATISFIED
7+
\[main.coverage.1\] file test.c line \d+ function main block 1 \(lines test.c:main:4\): SATISFIED
8+
^EXIT=0$
9+
^SIGNAL=0$
10+
--
11+
^warning: ignoring

src/goto-instrument/cover.cpp

Lines changed: 20 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -164,6 +164,9 @@ void parse_cover_options(const cmdlinet &cmdline, optionst &options)
164164
options.set_option(
165165
"cover-traces-must-terminate",
166166
cmdline.isset("cover-traces-must-terminate"));
167+
options.set_option(
168+
"cover-failed-assertions",
169+
cmdline.isset("cover-failed-assertions"));
167170
}
168171

169172
/// Build data structures controlling coverage from command-line options.
@@ -223,6 +226,9 @@ cover_configt get_cover_config(
223226
cover_config.traces_must_terminate =
224227
options.get_bool_option("cover-traces-must-terminate");
225228

229+
cover_config.cover_failed_assertions =
230+
options.get_bool_option("cover-failed-assertions");
231+
226232
return cover_config;
227233
}
228234

@@ -285,16 +291,22 @@ static void instrument_cover_goals(
285291
// Simplify the common case where we have ASSERT(x); ASSUME(x):
286292
if(i_it->is_assert())
287293
{
288-
auto successor = std::next(i_it);
289-
if(
290-
successor != function.body.instructions.end() &&
291-
successor->is_assume() &&
292-
successor->get_condition() == i_it->get_condition())
294+
if(!cover_config.cover_failed_assertions)
293295
{
294-
successor->turn_into_skip();
296+
auto successor = std::next(i_it);
297+
if(
298+
successor != function.body.instructions.end() &&
299+
successor->is_assume() &&
300+
successor->get_condition() == i_it->get_condition())
301+
{
302+
successor->turn_into_skip();
303+
}
304+
i_it->type = goto_program_instruction_typet::ASSUME;
305+
}
306+
else
307+
{
308+
i_it->turn_into_skip();
295309
}
296-
297-
i_it->type = goto_program_instruction_typet::ASSUME;
298310
}
299311
}
300312
}

src/goto-instrument/cover.h

Lines changed: 8 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -22,9 +22,14 @@ class message_handlert;
2222
class cmdlinet;
2323
class optionst;
2424

25-
#define OPT_COVER "(cover):"
25+
#define OPT_COVER \
26+
"(cover):" \
27+
"(cover-failed-assertions)"
28+
2629
#define HELP_COVER \
27-
" --cover CC create test-suite with coverage criterion CC\n"
30+
" --cover CC create test-suite with coverage criterion CC\n" /* NOLINT(*) */ \
31+
" --cover-failed-assertions do not stop coverage checking at failed assertions\n" /* NOLINT(*) */ \
32+
" (this is the default for --cover assertions)\n"
2833

2934
enum class coverage_criteriont
3035
{
@@ -41,6 +46,7 @@ enum class coverage_criteriont
4146
struct cover_configt
4247
{
4348
bool keep_assertions;
49+
bool cover_failed_assertions;
4450
bool traces_must_terminate;
4551
irep_idt mode;
4652
function_filterst function_filters;

0 commit comments

Comments
 (0)