Skip to content

CBMC: Pass uninitialized pointers in all verification harnesses #340

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

Merged
merged 1 commit into from
Nov 5, 2024

Conversation

hanno-becker
Copy link
Contributor

@hanno-becker hanno-becker commented Nov 4, 2024

Previously, when a function under proof would assume a pointer to a structure, the verification harness would construct an instance of that structure on the stack and pass its address.

This approach is unsound, because it adds to the contractual assumptions of the function the specifics of the function invocation in the test harness. For example, a missing bounds constraint in the spec might go undetected just because the stack-allocated variable happens to satisfy it.

The most robust way to deal with this, so it seems, is to minimize the harnesses to merely pass uninitialized variables of the right type to the function under proof. In particular, where a pointer is expected, pass an uninitialized pointer, rather than the address of a stack allocated structure.

Also, remove redundant x != NULL preconditions when IS_FRESH(x,...)
is assumed. This is not only redundant, but also error prone because of
diffblue/cbmc#8492.

This commit implements this change for all harnesses implemented so far.

Previously, when a function under proof would assume a pointer to
a structure, the verification harness would construct an instance
of that structure on the stack and pass its address.

This approach is unsound, because it adds to the contractual assumptions
of the function the specifics of the function invocation in the test
harness. For example, a missing bounds constraint in the spec might
go undetected just because the stack-allocated variable happens to
satisfy it.

The most robust way to deal with this, so it seems, is to minimize
the harnesses to merely pass uninitialized variables of the right type
to the function under proof. In particular, where a pointer is expected,
pass an uninitialized pointer, rather than the address of a stack allocated
structure.

Also, remove redundant `x != NULL` preconditions when `IS_FRESH(x,...)`
is assumed. This is not only redundant, but also error prone because of
diffblue/cbmc#8492.

This commit implements those changes for all harnesses implemented so far.

As it turns out, a few specs were incorrect because of missing IS_FRESH
annotations, hidden by the correct allocation in the harness.

Signed-off-by: Hanno Becker <[email protected]>
Copy link
Contributor

@mkannwischer mkannwischer left a comment

Choose a reason for hiding this comment

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

Thanks @hanno-becker. This looks good to me. I double checked that you have not missed any instances. Please make sure to adjust #306 with the same changes before you merge it.

@hanno-becker hanno-becker merged commit 4eae16a into main Nov 5, 2024
27 checks passed
@hanno-becker hanno-becker deleted the cbmc_harness_cleanup branch November 5, 2024 05:43
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.

2 participants