diff options
author | bstarynk <bstarynk@138bc75d-0d04-0410-961f-82ee72b054a4> | 2011-05-11 11:13:27 +0000 |
---|---|---|
committer | bstarynk <bstarynk@138bc75d-0d04-0410-961f-82ee72b054a4> | 2011-05-11 11:13:27 +0000 |
commit | c41143fb1d63596ff2a0f6da741b4bae73b8be16 (patch) | |
tree | d70c0763693cfef7bc877f21e079986944261a5f /gcc/gcov.c | |
parent | eb0badc13724022c8828a55e516d0eecdc487cc3 (diff) | |
download | gcc-c41143fb1d63596ff2a0f6da741b4bae73b8be16.tar.gz |
2011-05-11 Basile Starynkevitch <basile@starynkevitch.net>
MELT branch merged with trunk rev 173647 using svnmerge
git-svn-id: svn+ssh://gcc.gnu.org/svn/gcc/branches/melt-branch@173652 138bc75d-0d04-0410-961f-82ee72b054a4
Diffstat (limited to 'gcc/gcov.c')
-rw-r--r-- | gcc/gcov.c | 65 |
1 files changed, 42 insertions, 23 deletions
diff --git a/gcc/gcov.c b/gcc/gcov.c index 2fbeaf55e53..27ae036740a 100644 --- a/gcc/gcov.c +++ b/gcc/gcov.c @@ -54,6 +54,13 @@ along with Gcov; see the file COPYING3. If not see some places we make use of the knowledge of how profile.c works to select particular algorithms here. */ +/* The code validates that the profile information read in corresponds + to the code currently being compiled. Rather than checking for + identical files, the code below computes a checksum on the CFG + (based on the order of basic blocks and the arcs in the CFG). If + the CFG checksum in the gcda file match the CFG checksum for the + code currently being compiled, the profile data will be used. */ + /* This is the size of the buffer used to read in source file lines. */ #define STRING_SIZE 200 @@ -161,7 +168,8 @@ typedef struct function_info /* Name of function. */ char *name; unsigned ident; - unsigned checksum; + unsigned lineno_checksum; + unsigned cfg_checksum; /* Array of basic blocks. */ block_t *blocks; @@ -661,10 +669,8 @@ create_file_names (const char *file_name) int base; /* Free previous file names. */ - if (bbg_file_name) - free (bbg_file_name); - if (da_file_name) - free (da_file_name); + free (bbg_file_name); + free (da_file_name); da_file_name = bbg_file_name = NULL; bbg_file_time = 0; bbg_stamp = 0; @@ -728,7 +734,7 @@ find_source (const char *file_name) file_name = "<unknown>"; for (src = sources; src; src = src->next) - if (!strcmp (file_name, src->name)) + if (!filename_cmp (file_name, src->name)) break; if (!src) @@ -809,12 +815,14 @@ read_graph_file (void) if (tag == GCOV_TAG_FUNCTION) { char *function_name; - unsigned ident, checksum, lineno; + unsigned ident, lineno; + unsigned lineno_checksum, cfg_checksum; source_t *src; function_t *probe, *prev; ident = gcov_read_unsigned (); - checksum = gcov_read_unsigned (); + lineno_checksum = gcov_read_unsigned (); + cfg_checksum = gcov_read_unsigned (); function_name = xstrdup (gcov_read_string ()); src = find_source (gcov_read_string ()); lineno = gcov_read_unsigned (); @@ -822,7 +830,8 @@ read_graph_file (void) fn = XCNEW (function_t); fn->name = function_name; fn->ident = ident; - fn->checksum = checksum; + fn->lineno_checksum = lineno_checksum; + fn->cfg_checksum = cfg_checksum; fn->src = src; fn->line = lineno; @@ -1109,7 +1118,8 @@ read_count_file (void) if (!fn) ; - else if (gcov_read_unsigned () != fn->checksum) + else if (gcov_read_unsigned () != fn->lineno_checksum + || gcov_read_unsigned () != fn->cfg_checksum) { mismatch:; fnotice (stderr, "%s:profile mismatch for '%s'\n", @@ -1527,7 +1537,7 @@ make_gcov_file_name (const char *input_name, const char *src_name) if (flag_preserve_paths) { - /* Convert '/' and '\' to '#', remove '/./', convert '/../' to '/^/', + /* Convert '/' and '\' to '#', remove '/./', convert '/../' to '#^#', convert ':' to '~' on DOS based file system. */ char *pnew = name, *pold = name; @@ -1535,33 +1545,42 @@ make_gcov_file_name (const char *input_name, const char *src_name) while (*pold != '\0') { - if (*pold == '/' || *pold == '\\') - { - *pnew++ = '#'; - pold++; - } #if defined (HAVE_DOS_BASED_FILE_SYSTEM) - else if (*pold == ':') + if (*pold == ':') { *pnew++ = '~'; pold++; } + else #endif - else if ((*pold == '/' && strstr (pold, "/./") == pold) - || (*pold == '\\' && strstr (pold, "\\.\\") == pold)) + if ((*pold == '/' + && (strstr (pold, "/./") == pold + || strstr (pold, "/.\\") == pold)) + || (*pold == '\\' + && (strstr (pold, "\\.\\") == pold + || strstr (pold, "\\./") == pold))) pold += 3; - else if (*pold == '/' && strstr (pold, "/../") == pold) + else if (*pold == '/' + && (strstr (pold, "/../") == pold + || strstr (pold, "/..\\") == pold)) { - strcpy (pnew, "/^/"); + strcpy (pnew, "#^#"); pnew += 3; pold += 4; } - else if (*pold == '\\' && strstr (pold, "\\..\\") == pold) + else if (*pold == '\\' + && (strstr (pold, "\\..\\") == pold + || strstr (pold, "\\../") == pold)) { - strcpy (pnew, "\\^\\"); + strcpy (pnew, "#^#"); pnew += 3; pold += 4; } + else if (*pold == '/' || *pold == '\\') + { + *pnew++ = '#'; + pold++; + } else *pnew++ = *pold++; } |