Reputation: 37
Here's a small C program I wrote:
#include <stdio.h>
#include <stdlib.h>
/* Prototypes */
int sum(int *summands, unsigned int n);
void increment(char *string, int n);
void copy(char *src, char *dst);
int main(void)
{
int arr[] = {1, 2, 3, 4, 5, 6, 7, 8, 9};
char str1[] = "HAL";
char str2[] = "SRIKANT";
char str3[] = "A string to be copied.";
char *str4 = malloc(sizeof(str3));
printf("The sum of all the elements in ARR is %d.\n", sum(arr, 9));
printf("STR1 is: %s. STR2 is: %s.\n", str1, str2);
printf("Incrementing all letters...\n");
increment(str1, 3);
increment(str2, 7);
printf("Incremented!\n");
printf("STR1 is now: %s. STR2 is now: %s.\n", str1, str2);
copy(str3, str4);
printf("STR4 is: %s\n", str4);
free(str4);
return 0;
}
/* Returns the sum of all the elements in SUMMANDS. */
int sum(int *summands, unsigned int n)
{
int sum = 0;
for (int i = 0; i < (int) n; i++)
{
sum += *(summands + i);
}
return sum;
}
/* Increments all the letters in the string STRING, held in an array of length N.
* Does not modify any other memory which has been previously allocated. */
void increment(char *string, int n)
{
for (int i = 0; i < n; i++)
{
(*(string + i))++;
}
}
/* Copies the string SRC to DST. */
// void copy(char *src, char *dst)
// {
// while (*src)
// {
// *dst++ = *src++;
// }
// *dst = '\0';
// }
void copy(char *src, char *dst)
{
while ((*dst++ = *src++));
}
When I run the executable with Valgrind on my machine running Linux Mint 18, it produces the following erroneous report (heap summary):
==5503== Memcheck, a memory error detector
==5503== Copyright (C) 2002-2015, and GNU GPL'd, by Julian Seward et al.
==5503== Using Valgrind-3.11.0 and LibVEX; rerun with -h for copyright info
==5503== Command: ./disc1_q4
==5503==
The sum of all the elements in ARR is 45.
STR1 is: HAL. STR2 is: SRIKANT.
Incrementing all letters...
Incremented!
STR1 is now: IBM. STR2 is now: TSJLBOU.
STR4 is: A string to be copied.
==5503==
==5503== HEAP SUMMARY:
==5503== in use at exit: 0 bytes in 0 blocks
==5503== total heap usage: 2 allocs, 2 frees, 1,047 bytes allocated
==5503==
==5503== All heap blocks were freed -- no leaks are possible
==5503==
==5503== For counts of detected and suppressed errors, rerun with: -v
==5503== ERROR SUMMARY: 0 errors from 0 contexts (suppressed: 0 from 0)
But when I run the same program with Valgrind on the Cloud 9 IDE (which uses a Ubuntu virtual machine), it produces the correct report:
==2359== Memcheck, a memory error detector
==2359== Copyright (C) 2002-2013, and GNU GPL'd, by Julian Seward et al.
==2359== Using Valgrind-3.10.0.SVN and LibVEX; rerun with -h for copyright info
==2359== Command: ./disc1_q4
==2359==
The sum of all the elements in ARR is 45.
STR1 is: HAL. STR2 is: SRIKANT.
Incrementing all letters...
Incremented!
STR1 is now: IBM. STR2 is now: TSJLBOU.
STR4 is: A string to be copied.
==2359==
==2359== HEAP SUMMARY:
==2359== in use at exit: 0 bytes in 0 blocks
==2359== total heap usage: 1 allocs, 1 frees, 23 bytes allocated
==2359==
==2359== All heap blocks were freed -- no leaks are possible
==2359==
==2359== For counts of detected and suppressed errors, rerun with: -v
==2359== ERROR SUMMARY: 0 errors from 0 contexts (suppressed: 0 from 0)
Why is Valgrind producing incorrect results on my machine?
Upvotes: 1
Views: 136
Reputation: 121417
I suspect printf()
allocates memory in one case which you think as "erroneous".
It wouldn't be unrealistic for your libc's printf()
implementation allocates some memory internally; it's not erroneous.
Valgrind catches all the allocations and reports it even though your program itself didn't allocate it. You can test this by commenting out the printf()
's. Similarly, other standard functions could do memory allocations as well. So, you can't control it and there are not "wrong". You don't need to worry about the "total allocations" as long as there's no leak reported.
Upvotes: 1