Reputation: 85
ive got a C program that gets caught in a for loop that it shouldn't, running it with
valgrind --tool=memcheck --leak-check=yes a.out
doesnt return anything even up until the program gets caught. is there a way to change the settings of valgrind to help me find the leak? as many have pointed out, it wouldnt be considered a leak, apologies
thanks in advance
here is the loop in question
int clockstate=0;
int clocklength=0;
int datalength=0;
int datastate=0;
int dataloc = 9;
((((some other code that i don't think is important to this part))))
int dataerr[13] = {0};
int clockerr[13] = {0}; // assumes that spill does not change within an event.
int spill=0;
int k = 0;
spill = Getspill(d+4*255+1); // get spill bit from around the middle
//printf("got spill: %d \n", spill); // third breakpoint
for( k = 0; k < 512; k++)
{
// Discardheader(d); // doesnt actually do anything, since it's a header.f
int databit = Getexpecteddata(d+4*k+1);
printf("%d ",k);
int transmitted = Datasample(&datastate, &datalength, d+4*k+2,dataerr,dataloc, databit);
printf("%d ",k);
Clocksample(&clockstate, &clocklength, d+4*k+3,clockerr, transmitted);
printf("%d \n",k);
// assuming only one error per event (implying the possibility of multi-error "errors"
// we construct the final error at the very end of the (outside this loop)
}
and the loop repeats after printing
254 254 254
255 255 255
256 256 1 <- this is the problem
2 2 2
3 3 3
edit** so i've tracked down where it is happening, and at one point in
void Clocksample (int* state, int* length, char *d, int *type, int transbit);
i have code that says *length = 1;
so it seems that this command is somehow writing onto int k
. my question now is, how did this happen, why isnt it changing length
back to one like i want, and how do i fix it. if you want, i can post the whole code to Clocksample
Upvotes: 1
Views: 881
Reputation: 213375
Please note that Valgrind is exceedingly weak when it comes to detecting stack buffer overflows (which is what appears to be happening here).
Google address-sanitizer is much better at detecting stack overflows, and I suggest you try it instead.
Upvotes: 2
Reputation: 6543
So your debugging output indicates that k
is being changed during the call to your function Clocksample
. I see that you are passing the addresses of at least two variables, &clockstate
and &clocklength
into that call. It seems quite likely to me that you have an array overrun or some other wild pointer in Clocksample
that ends up overwriting the memory location where k
is stored.
It might be possible to narrow down the bug if you post the code where k
is declared (and whatever other variables are declared nearby in the same scope). For example if clocklength
is declared right before k
then you probably have a bug in using the pointer value &clocklength
that leads to writing past the end of clocklength
and corrupting k
. But it's hard to know for sure without having the actual layout of variables you're using.
valgrind doesn't catch this because if, say, clocklength
and k
are right next to each other on the stack, valgrind can't tell if you have a perfectly valid access to k
or a buggy access past the end of clocklength
, since all it checks is what memory you actually access.
Upvotes: 1
Reputation: 340168
Similar to last time, something in one of those functions, Clocksample()
this time, is writing to memory that doesn't belong to the data/arrays that the function should be using. Most likely an out of bounds array write. Note: this is not a memory leak, which is allocating then losing track of memory blocks that should be freed.
Set a breakpoint at the call to Clocksample()
for when k
is 256. Then step into Clocksample()
, keeping a watch on k
(or the memory used by k
). You can probably also just set a hardware memory write breakpoint on the memory allocated to k
. How you do any of this depends on the debugger you're using.
Now single-step (or just run to the return of Clocksample()
if you have a hardware breakpoint set) and when k
changes, you'll have the culprit.
Upvotes: 2