uncovered path (wrong constraint?)

I clang the following code, but the expected warning is missing.
Could it be that i is being constrained to zero, and this constraint is not
being removed by the while statement?

void use(int);

void checkchecker(char *s) {
  int i=0;
  int j;
  while(*s!=0) {
    i++;
  }
  if(i>0) {
    use(j); // expected warning: Function call argument is an uninitialized
value
  }
}

If I change the if-predicate to "i==0", the warning is being reported.

Thanks, Yuval.

Did you mean *(s++)!=0? The way you wrote this loop, 's' doesn't change, so either you skip over the loop or it becomes an infinite loop.

(Infinite loops would be another nice thing for the analyzer to catch but there are of course reasons why it is tricky.)

Jordan

yes, sorry for this mistake.
I was trying to build a small program to understand why not all paths are
covered.
How about this example:

void use(int);
void checkchecker(char *s) {
  int i=0;
  int j;
  while(*(s++)!=0) {
    i++;
  }
  if(i>4) {
    use(j); //no report - if predicate is changed to i<4 there is a report
  }
}

I see in the code that loops are covered 4 times, but I'd like to add
another path and remove all constraints on variables that are changed in the
loop (in the style of a widening operation). Any ideas on how to do this?
Thanks, Yuval

Yuval,

Unfortunately, we do not currently have the widening implemented. It’s an open project of non-trivial complexity (See http://clang-analyzer.llvm.org/open_projects.html). Let us know if you would like to work on solving this problem.

Cheers,
Anna.

yes, sorry for this mistake.
I was trying to build a small program to understand why not all paths are
covered.
How about this example:

void use(int);
void checkchecker(char *s) {
  int i=0;
  int j;
  while(*(s++)!=0) {
    i++;
  }
  if(i>4) {
    use(j); //no report - if predicate is changed to i<4 there is a report
  }
}

I see in the code that loops are covered 4 times,

Hi, Yuval.

There is an analyzer option -analyzer-max-loop <value> that establishes how many times the analyzer iterates the loop.
In your example if the contents of 's' is unknown the loop will iterate up to this value.

but I'd like to add
another path and remove all constraints on variables that are changed in the
loop (in the style of a widening operation). Any ideas on how to do this?
Thanks, Yuval

As I understand the analyzer tries to cover all possible paths. In your example the first paths is when the while condition is considered false at the very beginning and the loop iterates 0 times; the following code illustrates this:

void use(int);
void checkchecker(char *s) {
     int i=0;
     int j;
     int k;
     while(*(s++)!=0) {
         i++;
                 k = 0;
     }
         use(k);
}

z_zzz.cpp:11:9: warning: Function call argument is an uninitialized value
         use(k);
         ^ ~

Here no constrains from the loop are applied.
Does it help?

Anton, thanks for taking the time to review the code and answer.
I ran a few more tests and noticed that the analyzer never reaches the if statement.

Here’s a refined example to illustrate this:

void use(int);
void checkchecker(char s) {
int i=0;
int j;
int k;
while(
(s++)!=0) {
i++;
k = 0;
use(j);
}
if(i>0)
use(k);
}

pathtest.c:9:5: warning: Function call argument is an uninitialized value
use(j);
^ ~

As you can see, the analyzer does indeed walks through the while loop (therefore increments i), but never reaches into the if statement.
So as I understand , not all paths are covered. Am I missing something here?

Thanks again,
Yuval