Description
I've got the poison, but I think @thk123 may have the remedy. It seems there are a number of problems here:
-
function pointer removal doesn't account for the possibility of NULL. Maybe we should create a __CPROVER_invalid_function_pointer() function which contains a single dereference of a NULL pointer so that the options for pointer instrumentation just work. This could then be added as an else condition on the function pointer dereference to handle all manner of pointer corruption.
-
I'm not sure why the assignment is not being handled correctly.
$ cat null-function-pointers.c
#include <assert.h>
#include <stdlib.h>
typedef void(*fp)(void);
void f00 (void) {
assert(0);
return;
}
int main (int argc, char **argv) {
fp ptr = &f00;
ptr = NULL;
ptr();
return 1;
}
$ cbmc null-function-pointers.c
CBMC version 5.6 64-bit x86_64 linux
Parsing null-function-pointers.c
Converting
Type-checking null-function-pointers
Generating GOTO Program
Adding CPROVER library (x86_64)
Removal of function pointers and virtual functions
Partial Inlining
Generic Property Instrumentation
Starting Bounded Model Checking
size of program expression: 47 steps
simple slicing removed 7 assignments
Generated 1 VCC(s), 1 remaining after simplification
Passing problem to propositional reduction
converting SSA
Running propositional reduction
Post-processing
Solving with MiniSAT 2.2.1 with simplifier
404 variables, 604 clauses
SAT checker: instance is SATISFIABLE
Runtime decision procedure: 0.005s
** Results:
[f00.assertion.1] assertion 0: FAILURE
** 1 of 1 failed (1 iteration)
VERIFICATION FAILED
$ goto-instrument --remove-function-pointers --show-goto-functions null-function-pointers.goto
Reading GOTO program from `null-function-pointers.goto'
Function Pointer Removal
Virtual function removal
Java instanceof removal
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
main /* main */
// 0 file null-function-pointers.c line 12 function main
void (ptr)(void);
// 1 file null-function-pointers.c line 12 function main
ptr = f00;
// 2 file null-function-pointers.c line 13 function main
ptr = (void ()(void))(void *)0;
// 3 file null-function-pointers.c line 15 function main
ptr;
// 4 file null-function-pointers.c line 15 function main
IF ptr == f00 THEN GOTO 1
// 5 file null-function-pointers.c line 15 function main
1: f00();
// 6 file null-function-pointers.c line 17 function main
return 1;
// 7 file null-function-pointers.c line 17 function main
dead ptr;
// 8 file null-function-pointers.c line 18 function main
END_FUNCTION