forked from Imagelibrary/binutils-gdb
* hist.h (struct histogram)
(histograms, num_histograms): New. * hist.c (find_histogram, find_histogram_for_pc) (read_histogram_header): New. (s_lowpc, s_highpc, lowpc, highpc, hist_num_bins) (hist_sample): Remove. (hist_read_rec): Use the above, and handle multiple histogram records with disjoint address ranges. (hist_write_hist): Support several histogram records. (scale_and_align_entries): Adjust for multiple histograms. (hist_assign_samples_1): New. (hist_assign_samples): Use the above. (hist_clip_symbol_address): New. * hist.h (hist_check_address) (hist_clip_symbol_address): Declare. * gmon_io.c (gmon_out_read, gmon_out_write): Adjust handling of legacy format for multiple histogram changes. * corefile.c (find_call): Check for core_text_space and clip symbol address range here. * vax.c (vax_find_call): Don't check for core_text_space, or clip the symbol's address range here. Use hist_check_address to check call's target address. * sparc.c: Likewise. * tahoe.c: Likewise. * i386.c: Likewise. * mips.c: Likewise. Also use core_text_sect->vma as the base address for code accesses, just like other machine-specific routines do. * gprof.texi: Adjust for the new logic.
This commit is contained in:
@@ -388,10 +388,10 @@ gmon_out_read (const char *filename)
|
||||
int samp_bytes, header_size = 0;
|
||||
unsigned long count;
|
||||
bfd_vma from_pc, self_pc;
|
||||
static struct hdr h;
|
||||
UNIT raw_bin_count;
|
||||
struct hdr tmp;
|
||||
unsigned int version;
|
||||
unsigned int hist_num_bins;
|
||||
|
||||
/* Information from a gmon.out file is in two parts: an array of
|
||||
sampling hits within pc ranges, and the arcs. */
|
||||
@@ -430,7 +430,7 @@ gmon_out_read (const char *filename)
|
||||
if (gmon_io_read_32 (ifp, &profrate))
|
||||
goto bad_gmon_file;
|
||||
|
||||
if (!s_highpc)
|
||||
if (!histograms)
|
||||
hz = profrate;
|
||||
else if (hz != (int) profrate)
|
||||
{
|
||||
@@ -480,35 +480,37 @@ gmon_out_read (const char *filename)
|
||||
done (1);
|
||||
}
|
||||
|
||||
if (s_highpc && (tmp.low_pc != h.low_pc
|
||||
|| tmp.high_pc != h.high_pc || tmp.ncnt != h.ncnt))
|
||||
samp_bytes = tmp.ncnt - header_size;
|
||||
hist_num_bins = samp_bytes / sizeof (UNIT);
|
||||
if (histograms && (tmp.low_pc != histograms->lowpc
|
||||
|| tmp.high_pc != histograms->highpc
|
||||
|| (hist_num_bins != histograms->num_bins)))
|
||||
{
|
||||
fprintf (stderr, _("%s: incompatible with first gmon file\n"),
|
||||
filename);
|
||||
done (1);
|
||||
}
|
||||
|
||||
h = tmp;
|
||||
s_lowpc = (bfd_vma) h.low_pc;
|
||||
s_highpc = (bfd_vma) h.high_pc;
|
||||
lowpc = (bfd_vma) h.low_pc / sizeof (UNIT);
|
||||
highpc = (bfd_vma) h.high_pc / sizeof (UNIT);
|
||||
samp_bytes = h.ncnt - header_size;
|
||||
hist_num_bins = samp_bytes / sizeof (UNIT);
|
||||
if (!histograms)
|
||||
{
|
||||
histograms = xmalloc (sizeof (struct histogram));
|
||||
histograms->lowpc = tmp.low_pc;
|
||||
histograms->highpc = tmp.high_pc;
|
||||
histograms->num_bins = hist_num_bins;
|
||||
histograms->sample = xmalloc (hist_num_bins * sizeof (int));
|
||||
memset (histograms->sample, 0,
|
||||
hist_num_bins * sizeof (int));
|
||||
}
|
||||
|
||||
DBG (SAMPLEDEBUG,
|
||||
printf ("[gmon_out_read] lowpc 0x%lx highpc 0x%lx ncnt %d\n",
|
||||
(unsigned long) h.low_pc, (unsigned long) h.high_pc,
|
||||
h.ncnt);
|
||||
printf ("[gmon_out_read] s_lowpc 0x%lx s_highpc 0x%lx\n",
|
||||
(unsigned long) s_lowpc, (unsigned long) s_highpc);
|
||||
printf ("[gmon_out_read] lowpc 0x%lx highpc 0x%lx\n",
|
||||
(unsigned long) lowpc, (unsigned long) highpc);
|
||||
(unsigned long) tmp.low_pc, (unsigned long) tmp.high_pc,
|
||||
tmp.ncnt);
|
||||
printf ("[gmon_out_read] samp_bytes %d hist_num_bins %d\n",
|
||||
samp_bytes, hist_num_bins));
|
||||
|
||||
/* Make sure that we have sensible values. */
|
||||
if (samp_bytes < 0 || lowpc > highpc)
|
||||
if (samp_bytes < 0 || histograms->lowpc > histograms->highpc)
|
||||
{
|
||||
fprintf (stderr,
|
||||
_("%s: file '%s' does not appear to be in gmon.out format\n"),
|
||||
@@ -519,14 +521,6 @@ gmon_out_read (const char *filename)
|
||||
if (hist_num_bins)
|
||||
++nhist;
|
||||
|
||||
if (!hist_sample)
|
||||
{
|
||||
hist_sample =
|
||||
(int *) xmalloc (hist_num_bins * sizeof (hist_sample[0]));
|
||||
|
||||
memset (hist_sample, 0, hist_num_bins * sizeof (hist_sample[0]));
|
||||
}
|
||||
|
||||
for (i = 0; i < hist_num_bins; ++i)
|
||||
{
|
||||
if (fread (raw_bin_count, sizeof (raw_bin_count), 1, ifp) != 1)
|
||||
@@ -537,7 +531,8 @@ gmon_out_read (const char *filename)
|
||||
done (1);
|
||||
}
|
||||
|
||||
hist_sample[i] += bfd_get_16 (core_bfd, (bfd_byte *) raw_bin_count);
|
||||
histograms->sample[i]
|
||||
+= bfd_get_16 (core_bfd, (bfd_byte *) raw_bin_count);
|
||||
}
|
||||
|
||||
/* The rest of the file consists of a bunch of
|
||||
@@ -684,9 +679,10 @@ gmon_out_write (const char *filename)
|
||||
|
||||
/* Write the parts of the headers that are common to both the
|
||||
old BSD and 4.4BSD formats. */
|
||||
if (gmon_io_write_vma (ofp, s_lowpc)
|
||||
|| gmon_io_write_vma (ofp, s_highpc)
|
||||
|| gmon_io_write_32 (ofp, hist_num_bins * sizeof (UNIT) + hdrsize))
|
||||
if (gmon_io_write_vma (ofp, histograms->lowpc)
|
||||
|| gmon_io_write_vma (ofp, histograms->highpc)
|
||||
|| gmon_io_write_32 (ofp, histograms->num_bins
|
||||
* sizeof (UNIT) + hdrsize))
|
||||
{
|
||||
perror (filename);
|
||||
done (1);
|
||||
@@ -714,9 +710,9 @@ gmon_out_write (const char *filename)
|
||||
}
|
||||
|
||||
/* Dump the samples. */
|
||||
for (i = 0; i < hist_num_bins; ++i)
|
||||
for (i = 0; i < histograms->num_bins; ++i)
|
||||
{
|
||||
bfd_put_16 (core_bfd, (bfd_vma) hist_sample[i],
|
||||
bfd_put_16 (core_bfd, (bfd_vma) histograms->sample[i],
|
||||
(bfd_byte *) &raw_bin_count[0]);
|
||||
if (fwrite (&raw_bin_count[0], sizeof (raw_bin_count), 1, ofp) != 1)
|
||||
{
|
||||
|
||||
Reference in New Issue
Block a user