c - Do I need to worry about Valgrind reporting errors outside the scope of my application? -


when running valgrind's memcheck tool, many hundreds of thousands (or more, since valgrind cuts off @ 100k) of small invalid read statements, e.g.:

==32027== invalid read of size 1 ==32027==    @ 0x3ab426e26a: _io_default_xsputn (in /lib64/libc-2.5.so) ==32027==    0x3ab426cf70: _io_file_xsputn@@glibc_2.2.5 (in /lib64/libc-2.5.so) ==32027==    0x3ab42621fa: fwrite (in /lib64/libc-2.5.so) ==32027==    0x4018ca: starch_gzip_deflate (in /home/areynolds/trunk/utility/applications/bed/starch/bin/starch) ==32027==    0x401f48: compressfilewithgzip (in /home/areynolds/trunk/utility/applications/bed/starch/bin/starch) ==32027==    0x4028b5: transforminput (in /home/areynolds/trunk/utility/applications/bed/starch/bin/starch) ==32027==    0x402f12: main (in /home/areynolds/trunk/utility/applications/bed/starch/bin/starch) ==32027==  address 0x7febb9b3c on thread 1's stack 

these statements refer calls functions outside of application ("starch") , appear part of libc. need concerned with?

edit

if modify fwrite call remove 1 byte, gzip stream gets corrupted. here's original code:

int starch_gzip_deflate(file *source, file *dest, int level) {                                                                                                                                                                                                                    int ret, flush;                                                                                                                                                                                                                                                              unsigned have;                                                                                                                                                                                                                                                               z_stream strm;                                                                                                                                                                                                                                                               unsigned char in[starch_z_chunk];                                                                                                                                                                                                                                            unsigned char out[starch_z_chunk];                                                                                                                                                                                                                                            /* initialize deflate state */                                                                                                                                                                                                                                                 strm.zalloc = z_null;                                                                                                                                                                                                                                                        strm.zfree = z_null;                                                                                                                                                                                                                                                         strm.opaque = z_null;                                                                                                                                                                                                                                                         /* deflateinit2 allows creation of archive gzip header, i.e. gzip file */                                                                                                                                                                                             /* cf. http://www.zlib.net/manual.html */                                                                                                                                                                                                                                    ret = deflateinit2(&strm, level, z_deflated, (15+16), 8, z_default_strategy);                                                                                                                                                                                                if (ret != z_ok)                                                                                                                                                                                                                                                                 return ret;                                                                                                                                                                                                                                                               /* compress until end of file */                                                                                                                                                                                                                                             {                                                                                                                                                                                                                                                                             strm.avail_in = fread(in, 1, starch_z_chunk, source);                                                                                                                                                                                                                        if (ferror(source)) {                                                                                                                                                                                                                                                            (void)deflateend(&strm);                                                                                                                                                                                                                                                     return z_errno;                                                                                                                                                                                                                                                          }                                                                                                                                                                                                                                                                            flush = feof(source) ? z_finish : z_no_flush;                                                                                                                                                                                                                                strm.next_in = in;                                                                                                                                                                                                                                                            {                                                                                                                                                                                                                                                                             strm.avail_out = starch_z_chunk;                                                                                                                                                                                                                                             strm.next_out = out;                                                                                                                                                                                                                                                         ret = deflate(&strm, flush);                                                                                                                                                                                                                                                 assert(ret != z_stream_error);                                                                                                                                                                                                                                               have = starch_z_chunk - strm.avail_out;                   /* invalid read happens here */                                                                                                                                                                                                                                 if (fwrite(out, 1, have, dest) != have || ferror(dest)) {                                                                                                                                                                                                                        (void)deflateend(&strm);                                                                                                                                                                                                                                                     return z_errno;                                                                                                                                                                                                                                                          }                                                                                                                                                                                                                                                                        } while (strm.avail_out == 0);                                                                                                                                                                                                                                               assert(strm.avail_in == 0);                                                                                                                                                                                                                                               } while (flush != z_finish);                                                                                                                                                                                                                                                 assert(ret == z_stream_end);                                                                                                                                                                                                                                                  /* clean , return */                                                                                                                                                                                                                                                    (void)deflateend(&strm);                                                                                                                                                                                                                                                     return z_ok;                                                                                                                                                                                                                                                             }    

edit 2

i think see problem. have in[starch_z_chunk] , not in[starch_z_chunk + 1] (and likewise out[]). if adjust both of fread , fwrite statements -1, don't seem invalid read of size 1 statements, although still see lot of invalid read of size 4 , 8 specific zlib:

==32624== invalid read of size 4 ==32624==    @ 0x3ab5206455: deflateinit2_ (in /usr/lib64/libz.so.1.2.3) ==32624==    0x40180e: starch_gzip_deflate (in /home/areynolds/trunk/utility/applications/bed/starch/bin/starch) ==32624==    0x401f48: compressfilewithgzip (in /home/areynolds/trunk/utility/applications/bed/starch/bin/starch) ==32624==    0x402c03: transforminput (in /home/areynolds/trunk/utility/applications/bed/starch/bin/starch) ==32624==    0x402f12: main (in /home/areynolds/trunk/utility/applications/bed/starch/bin/starch) ==32624==  address 0x7feafde38 on thread 1's stack 

edit 3

i recompiling -g which, mentioned, associate line numbers errors.

but i'm doing straightforward strncpy of argv[] variables, e.g.:

strncpy(uniqtag, argv[2], strlen(argv[2]) + 1); 

this should copy on null-terminated argv[2] string uniqtag, valgrind still marks error.

edit 4

here's error message:

==3682== invalid read of size 1 ==3682==    @ 0x4a081c1: strncpy (mc_replace_strmem.c:329) ==3682==    0x4022f1: parsecommandlineinputs (starch.c:589) ==3682==    0x402f20: main (starch.c:46) ==3682==  address 0x7fedffe11 on thread 1's stac 

here 2 relevant lines; valgrind saying second line invalid read:

uniqtag = (char *)malloc(strlen(argv[2]) + 1);  strncpy(uniqtag, argv[2], strlen(argv[2]) + 1); 

because strlen(argv[2]) + 1 > strlen(argv[2]), should result in null-terminated uniqtag.

in case i'd do. libc function arguments come program. i'd hazard guess , have off 1 error in code leads fwrite read 1 byte past end of source buffer.

edit:

by way, such small error can remain unseen (i.e. code not crash) because both compiler , memory allocator allocate memory blocks in specific sizes , align them @ word edges. means many times there small region past requested buffer end can access without triggering memory protection code. of course code might break if change compiler, libc, platform or bitness (e.g. go 64 32 bit).

valgrind has suppression lists expected errors in libc, can find @ /usr/lib64/valgrind/default.supp or /usr/lib/valgrind/default.supp. there quite few issues valgrind detects in libc, many of them intentional in effort optimise code, due suppresions in 99% of cases it's tested code causes problem.

edit2:

keep in mind that, debugging tools, valgrind output infinitely more useful information on issues detects if compile code debugging symbols. able point specific lines of code related issue - if quite not actual issue lies. if use gcc add -g options compile code debugging symbols. in production release, though, please remember remove flag!


Comments

Popular posts from this blog

android - Spacing between the stars of a rating bar? -

html - Instapaper-like algorithm -

c# - How to execute a particular part of code asynchronously in a class -