Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Restrict coverage data to coverage of reachable functions #36

Conversation

markrtuttle
Copy link
Contributor

@markrtuttle markrtuttle commented May 23, 2021

This pull request restricts the coverage calculation and reporting to those functions cbmc considers reachable functions (and not just all functions appearing in the goto binary).

This requires

  1. Adding the set of reachable functions as an optional parameter to the constructors for the various coverage classes (that extract coverage data from the various sources, like xml versus json coverage data).
  2. Moving the computation of reachable functions in the main viewer code to before the computation of the coverage data, and noting the path to the file json file that contains the reachable functions.
  3. Writing a function to filter the coverage data down to the the coverage data for the reachable functions. In the process, we wrote a sanity-checking predicate to confirm that coverage data reports no reachable lines in unreachable functions, and that we have some coverage data for each reachable function.

if not reachable_functions:
return coverage

def valid_coverage_data(coverage, reachable):

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

What does making this an inline function buy us?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I don't understand. It is used on only one place. What do you recommend that I do?

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

That was just a style question, not a criticism: wrapping it inside a function, vs just inlining the code. I was curious why you'd done the first for code that you only use once.

return valid

if not valid_coverage_data(coverage, reachable_functions):
logging.warning("Coverage calculations may not be accurate")

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

What do we do with these warnings? Does the user see them when they view the report?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The warnings are printed on the console when we summarize the coverage. Are you advocating that this be encoded in the json so it will appear on the report?

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

If possible, yes. Otherwise, a user interacting with the report via CI will not have an easy way to know there were warnings.

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Agree with @danielsn re adding to json.

@@ -142,12 +143,18 @@ def combine(self, status):
class Coverage:
"""CBMC coverage checking results"""

def __init__(self, coverage_list):
def __init__(self, coverage_list, viewer_reachable=None):
"""Load CBMC coverage data."""

# TODO: distinguish between coverage of source code and proof code
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Let's create Github issues instead of adding these comments here. #37

Comment on lines +254 to +258
if lines:
logging.warning(
"Unreachable function %s has reachable lines %s",
func_name, ', '.join([str(line) for line in sorted(lines)])
)
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

How can we have a unreachable function with reachable lines?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I'm concerned about the diffblue tools providing inconsistent information, I tried to drive that home with comments in the code referring to sanity checks.

@feliperodri feliperodri requested a review from karkhaz May 23, 2021 23:38
Copy link
Contributor

@feliperodri feliperodri left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LGTM.

@jimgrundy
Copy link

Can we address the request from @danielsn to get warnings into JSON so they aren't missed by CI users, and the try to advance this PR?

@markrtuttle
Copy link
Contributor Author

This pull request interacts badly with the --export-file-local flag. The static function foo in file.c is named __CPROVER_file_local_file_c_foo in the symbol table with pretty name foo. The --show-reachable-functions flag shows the function reachable with the name __CPROVER_file_local_file_c_foo, but reachable functions skips names with internal prefix __CPROVER. On the other hand, coverage data refers to the function as foo and not __CPROVER_file_local_file_c_foo.

Switching to draft pull request until this is fixed.

@markrtuttle markrtuttle marked this pull request as draft August 5, 2021 23:53
@markrtuttle
Copy link
Contributor Author

When complete, this pull request should close #69

@markrtuttle
Copy link
Contributor Author

Closing as cbmc support has improved since the original submission and there is now an easier implementation

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

5 participants