Re: [RFA]: printing symbols with > 32 bit addrs.

Michael Snyder
2001-02-28T20:33:00Z

Andrew Cagney wrote:
>
> Michael Snyder wrote:
> >
> >
> >
> > ------------------------------------------------------------------------
> > Oddly enough, info functions seems to fail to print addresses of
> > non-debugging symbols when addresses are greater than 32 bits.
> > This patch seems a bit crude, so I'm wondering if anyone has
> > a better suggestion.
>
> And non portable :-)
>
> > 2001-02-15 Michael Snyder <msnyder@mvstp600e.cygnus.com>
> >
> > * symtab.c (print_msymbol_info): Print addresses > 32 bits.
>
> (Kevin B has a useful cheat sheet of the int->text functions that he
> posted). At a guess paddr().

OK, how about this modification?
2001-02-28 Michael Snyder <msnyder@mvstp600e.cygnus.com>

* symtab.c (print_msymbol_info): Print addresses by portable method
longest_local_hex_string_custom. Allow for 64-bit addresses.

Index: symtab.c
===================================================================
RCS file: /cvs/src/src/gdb/symtab.c,v
retrieving revision 1.31
diff -c -3 -p -r1.31 symtab.c
*** symtab.c 2001/02/27 21:57:09 1.31
--- symtab.c 2001/03/01 04:31:15
*************** print_symbol_info (namespace_enum kind,
*** 2652,2660 ****
static void
print_msymbol_info (struct minimal_symbol *msymbol)
{
! printf_filtered (" %08lx %s\n",
! (unsigned long) SYMBOL_VALUE_ADDRESS (msymbol),
! SYMBOL_SOURCE_NAME (msymbol));
}

/* This is the guts of the commands "info functions", "info types", and
--- 2652,2667 ----
static void
print_msymbol_info (struct minimal_symbol *msymbol)
{
! char *tmp;
!
! if (TARGET_ADDR_BIT <= 32)
! tmp = longest_local_hex_string_custom (SYMBOL_VALUE_ADDRESS (msymbol),
! "08l");
! else
! tmp = longest_local_hex_string_custom (SYMBOL_VALUE_ADDRESS (msymbol),
! "016l");
! printf_filtered ("%s %s\n",
! tmp, SYMBOL_SOURCE_NAME (msymbol));
}

/* This is the guts of the commands "info functions", "info types", and
From kevinb@cygnus.com Thu Mar 01 00:16:00 2001
From: Kevin Buettner <kevinb@cygnus.com>
To: gdb-patches@sources.redhat.com
Subject: [SCRIPT] fixdates
Date: Thu, 01 Mar 2001 00:16:00 -0000
Message-id: <1010301081541.ZM18977@ocotillo.lan>
X-SW-Source: 2001-03/msg00000.html
Content-length: 11820

The patch below was used to generate the changes in the soon to be posted
copyright update/correction patch. This patch is (or at least should
be) at

http://sources.redhat.com/ml/gdb-patches/2001-02/msg00547.html

--- fixdates ---
#!/usr/bin/perl -w

# fixdates - Fix dates in copyright notices based upon ChangeLog entries
#
# Copyright 2001 Free Software Foundation, Inc.
#
# This file is free software; as a special exception the author gives
# unlimited permission to copy and/or distribute it, with or without
# modifications, as long as this notice is preserved.
#
# This program is distributed in the hope that it will be useful, but
# WITHOUT ANY WARRANTY, to the extent permitted by law; without even the
# implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.

# Written by Kevin Buettner <kevinb@redhat.com>
# Version 0.01

use Date::Manip;
use File::Basename;
use Getopt::Long;
use English;
use File::Find;

my $show_only;

# Get user supplied options; the only one defined for this program
# is --show-only which limits this script to scanning ChangeLog
# entries and printing the years associated with each file found.
GetOptions('show-only!' => \$show_only);

# After the options are disposed of, the first argument is the root.
my ($root) = @ARGV;

# Print a minimal usage message if the wrong number of arguments
# are supplied to the script.
if (!defined($root) || @ARGV > 1) {
die "Usage: $0 root\n";
}

# Construct a hash of predetermined filenames to exclude from
# consideration in GDB sources. These are either files that a
# maintainer has requested not be touched or are generated files.
my %exclude_files = map(("$root/$_", 1), qw {
go32-nat.c
ser-go32.c
config/djgpp/README
config/djgpp/config.sed
config/djgpp/djcheck.sh
config/djgpp/djconfig.sh
config/djgpp/fnchange.lst
config/i386/go32.mh
config/i386/go32.mt
config/i386/nm-go32.h
config/i386/tm-go32.h
config/i386/xm-go32.h

configure
doc/configure
gdbserver/configure
nlm/configure
rdi-share/configure
testsuite/configure
testsuite/gdb.asm/configure
testsuite/gdb.base/configure
testsuite/gdb.c++/configure
testsuite/gdb.chill/configure
testsuite/gdb.disasm/configure
testsuite/gdb.hp/gdb.aCC/configure
testsuite/gdb.hp/configure
testsuite/gdb.hp/gdb.base-hp/configure
testsuite/gdb.hp/gdb.compat/configure
testsuite/gdb.hp/gdb.defects/configure
testsuite/gdb.hp/gdb.objdbg/configure
testsuite/gdb.hp/gdb.threads-hp/configure
testsuite/gdb.java/configure
testsuite/gdb.mi/configure
testsuite/gdb.stabs/configure
testsuite/gdb.threads/configure
testsuite/gdb.trace/configure

gdbarch.c
gdbarch.h
});

# Reset the argument vector to the empty list.
@ARGV = ();

# Find all ChangeLog files; the paths to these files will be
# pushed onto @ARGV.
find(
sub {
if (-f && -T && /^ChangeLog/) {
push @ARGV, $File::Find::name;
}
},
$root
);

# Scan ChangeLog files looking for files and dates

my %cldat;
my ($date, $year);

$/ = ""; # slurp paragraphs

while (<>) {
if (not defined $dirprefix) {
$dirprefix = dirname($ARGV);
if ($dirprefix eq '.') {
$dirprefix = '';
}
else {
$dirprefix =~ s#^\./##;
$dirprefix .= '/';
}
}

chomp;

my ($name, $email, $datestr);
if (($datestr, $name, $email)
= / ^((?:\w.* (?:19|20)\d\d)|(?:\d\d\d\d-\d\d-\d\d))
# Date
\s+ # spaces
(\S+(?:\s+\S+)*) # name
\s+ # spaces
[(<] ([^)>]*) # email address
/x ) {

$date = ParseDateString($datestr);
$year = UnixDate ($date, "%Y");

# We won't be able to get a year out of a malformed date; if
# this happens, we'll examine the date string to try to determine
# the year.
if (!defined $year) {
($year) = $datestr =~ /((?:19|20)\d\d)/;
}
}
else {
my $filenames;
my $do_tabulate = 0;
my $para = $_;
while ($para =~ /^\s+ # leading spaces
\* # star
\s+ # trailing star spaces
([^(:]+?) # Filenames
(?: # Stop when we get to a
[(:] # paren or a colon
| # or a...
\s # space and a
\[ # left square bracket.
)
/mxg)
{
$filenames = $1;

$filenames =~ s/\n//g; # nuke newlines
$filenames =~ s/\s+$//; # remove trailing spaces

# Kill spaces after commas used in curly brace expansions.
while ($filenames =~ s/({[^}]*),\s+/$1,/) {}

# Attempt to handle case in which filenames are (erroneously)
# not comma separated. If there are no commas presently
# in the filename string and over half of the space
# separated "words" have a dot in the middle of them, they're
# considered a list of filenames.
if ($filenames !~ /,/) {
my @spsplit = split /\s+/, $filenames;
my @dotnames = grep /\.\w/, @spsplit;
if (@spsplit && scalar(@dotnames) / scalar(@spsplit) >= 0.5) {
$filenames = join (', ', @spsplit);
}
}

# Get list of file names.
my @filenames = map(expand_name($_), split( /,\s+/, $filenames));

# Discard names with spaces or other characters which
# aren't used in filenames in the GDB sources.
@filenames = grep !/[\s"'%]/, @filenames;

foreach my $fname (@filenames) {
$cldat{"$dirprefix$fname"}{$year}++;
}
}

}

if (eof) {
$dirprefix = undef;
close(ARGV);
}
}

# Show only the names and dates if that's what the user requested
if ($show_only) {
foreach my $fname (sort keys %cldat) {
print "$fname: ", join (', ', (sort keys %{$cldat{$fname}})), "\n";
}
exit 0;
}

# Weed out and warn about the names that don't exist or that we've
# intentionally decided to exclude; build new ARGV vector from those
# that seem okay
@ARGV = ();
foreach my $fname (sort keys %cldat) {
if (-e $fname) {
push @ARGV, $fname if (-f $fname && !$exclude_files{$fname});
}
else {
print STDERR "Warning: File ``$fname'' does not exist.\n"
}
}

# Fix the copyright notices in the remaining files

$INPLACE_EDIT = ''; # modify files in place
undef $/; # slurp entire files

while (<>) {
# Split buffer into two parts; the first fifteen lines had better
# contain the copyright notice.
my ($initial_lines, $remaining_lines) = m/\A((?:[^\n]*\n){0,15})(.*)\z/s;

# See if the initial lines contain a copyright notice to fix
if ($initial_lines =~
m/^ # beginning of a line
[^\n]* # anything but a newline
\bCopyright\b
[^\n]* # anything but newline
(?:\n[^\n]*){0,3}? # up to three additional
# lines, non-greedy
\bFree\b
[^\n]* # anything but newline
(?:\n[^\n]*?)?? # optional newline, plus
# portions of following line,
# non-greedy
\bSoftware\b
[^\n]* # anything but newline
(?:\n[^\n]*?)?? # optional newline, plus
# following stuff, non-greedy
\bFoundation\b
/xsm)
{
# Now fix the copyright notice.
$initial_lines =~
s{( ^ # beginning of line
[^\n]* # anything but newline
\bCopyright\b
.*? # anything, non-greedy
\bFree\b
.*? # anything, non-greedy
\bSoftware\b
.*?
\bFoundation
[^\n]* # anything but newline
$ # end of line
)}
{ fix_copyright($1, $ARGV) }xsme;
}
elsif ($initial_lines ne "") {
# Warn about (possible) bad or missing copyright notice.
print STDERR "Warning: Check $ARGV for missing or malformed copyright notice.\n";
}
# Write the buffer back out and go onto the next file.
print $initial_lines, $remaining_lines;
}

# Given a "glob" name, expand it into a list of equivalent names.
sub expand_name {
my ($name) = @_;

my ($prefix, $expansion, $suffix);

if (($prefix, $to_expand, $suffix) =
($name =~ /^
([^{]*]*) # prefix
{ # left curly
([^}]+) # stuff to expand
} # right curly
(.*) # suffix
$/x))
{
return map(expand_name($prefix . $_ . $suffix),
split(/,\s*/, $to_expand));
}
elsif (($prefix, $to_expand, $suffix) =
($name =~ /^
([^{]*]*) # prefix
\[ # left bracket
([^\]]+) # stuff to expand
\] # right bracket
(.*) # suffix
$/x))
{
return map(expand_name($prefix . $_ . $suffix),
split(/\0*/, $to_expand));
}
else {
return $name;
}
}

# Construct a corrected/updated copyright notice
sub fix_copyright {
my ($note, $fname) = @_;
my ($prefix1, $prefix2, $years);

($prefix1, $years, $prefix2) =
$note =~ /^(.*)Copyright(.*?)([^0-9]*)Free\s+(?:\1)?\s*Software\s+(?:\1)?\s*Foundation/s;

# Remove anything from the year string that is not a comma, digit, or
# hyphen
$years =~ s/[^0-9,-]//g;

# Figure out which dates are already in the copyright notice
my %years = ();

foreach my $yearspec (split /,/, $years) {
if ($yearspec =~ /^(\d+)-(\d+)$/) {
my ($initial, $final) = ($1, $2);
foreach ($initial, $final) {
$_ = "19" . $_ if length == 2;
}
if ($initial > $final) {
($initial, $final) = ($final, $initial);
}
next if ($initial < 1980);
next if ($final > 2001);
my $year;
for ($year = $initial; $year <= $final; $year++) {
$years{$year} = 1;
}
}
else {
$yearspec = "19" . $yearspec if length($yearspec) == 2;
next if $yearspec < 1980 || $yearspec > 2001;
$years{$yearspec} = 1;
}
}

my @newyears = sort keys %{$cldat{$fname}};
my @oldyears = sort keys %years;

# Discard ChangeLog years that are older than the oldest year
# in the original copyright notice. The reason for this is
# that if the file is rewritten, the notice may have been
# updated by hand to reflect this fact. Also, it's possible
# for a file to have been deleted and then years later reconstructed.
if (@oldyears) {
@newyears = grep($_ >= $oldyears[0], @newyears);
}

# Discard original copyright years that are newer than
# the oldest entry found in the ChangeLog. This allows
# us to construct a more accurate list.
if (@newyears) {
@oldyears = grep($_ < $newyears[0], @oldyears);
}

@newyears = (@oldyears, @newyears);

my $newcopyright = '';

# Handle cases where the Copyright notice doesn't start on
# its own line in .h and .c files.
if ($fname =~ /\.[hc]$/ && $prefix1 =~ /\S/ && length $prefix1 > 10) {
$prefix1 =~ s/\s+$//;
$newcopyright .= $prefix1;
$prefix1 =~ s/^(\s*)\S.*/$1/
}
my $line = $prefix1 . "Copyright ";

# If the prefix contains a C-style comment, then blank it out
# for subsequent lines
$prefix1 =~ s/\/\*/ /;

foreach my $year (@newyears) {
if (length $line > 70) {
$newcopyright .= "\n" if $newcopyright;
$line =~ s/ $//;
$newcopyright .= $line;
$line = $prefix1;
}
$line .= "$year, ";
}
$line =~ s/, $//;
my $fsfi = "Free Software Foundation, Inc.";
$newcopyright .= "\n" if $newcopyright;
if ($prefix2 =~ /\n/ || length($line) + length($fsfi) > 76) {
$newcopyright .= $line . "\n" . $prefix1 . $fsfi;
}
else {
$newcopyright .= $line . " " . $fsfi;
}

# Now handle the case of some other notice that occurred prior
# to finding "Free Software Foundation, Inc."
$prefix2 =~ s/^\s+//; # nuke leading spaces
$prefix2 =~ s/^\s$//; # nuke trailing spaces
if (length($prefix2) > length($prefix1)) {
$newcopyright .= "\n" . $prefix1 . $prefix2;
}

return $newcopyright;
}
--- end fixdates ---