From: Raphael Hertzog Date: Sun, 6 Jan 2008 17:07:07 +0000 (+0100) Subject: Dpkg::Shlibs::Objdump: Takes into account R_*_COPY relocations X-Git-Url: https://err.no/cgi-bin/gitweb.cgi?a=commitdiff_plain;h=e4ffa89209c478ad2fd2376e878398f99117a60a;p=dpkg Dpkg::Shlibs::Objdump: Takes into account R_*_COPY relocations * scripts/Dpkg/Shlibs/Objdump.pm: Also retrieve dynamic relocation records from objdump by adding the -R option. Use this information to mark symbols affected by R_*_COPY relocations as undefined. They are initialized by the loader with values searched in the needed libraries. --- diff --git a/ChangeLog b/ChangeLog index d577fe13..14a228cf 100644 --- a/ChangeLog +++ b/ChangeLog @@ -1,3 +1,11 @@ +2008-01-06 Raphael Hertzog + + * scripts/Dpkg/Shlibs/Objdump.pm: Also retrieve dynamic relocation + records from objdump by adding the -R option. Use this information + to mark symbols affected by R_*_COPY relocations as undefined. + They are initialized by the loader with values searched in the + needed libraries. + 2008-01-04 Raphael Hertzog * scripts/Dpkg/Shlibs/SymbolFile.pm: Replace #DEPRECATED by diff --git a/debian/changelog b/debian/changelog index 1d8ca660..46dfcc9b 100644 --- a/debian/changelog +++ b/debian/changelog @@ -12,6 +12,8 @@ dpkg (1.14.15) UNRELEASED; urgency=low tree to scan first when trying to find a needed library. * Change dpkg-gensymbols to mark symbols that disappeared with #MISSING instead of #DEPRECATED, it's clearer for people. + * Fix Dpkg::Shlibs::Objdump to properly take into account R_*_COPY + relocations. Closes: #454036 [ Guillem Jover ] * Move compression related variables to a new Dpkg::Compression module. diff --git a/scripts/Dpkg/Shlibs/Objdump.pm b/scripts/Dpkg/Shlibs/Objdump.pm index 21225561..859be1cd 100644 --- a/scripts/Dpkg/Shlibs/Objdump.pm +++ b/scripts/Dpkg/Shlibs/Objdump.pm @@ -129,6 +129,7 @@ sub reset { $self->{RPATH} = []; $self->{dynsyms} = {}; $self->{flags} = {}; + $self->{dynrelocs} = {}; return $self; } @@ -144,7 +145,7 @@ sub _read { $self->{file} = $file; local $ENV{LC_ALL} = 'C'; - open(my $objdump, "-|", "objdump", "-w", "-f", "-p", "-T", $file) + open(my $objdump, "-|", "objdump", "-w", "-f", "-p", "-T", "-R", $file) || syserr(sprintf(_g("Can't execute objdump: %s"), $!)); my $ret = $self->_parse($objdump); close($objdump); @@ -162,6 +163,10 @@ sub _parse { if (/^DYNAMIC SYMBOL TABLE:/) { $section = "dynsym"; next; + } elsif (/^DYNAMIC RELOCATION RECORDS/) { + $section = "dynreloc"; + $_ = <$fh>; # Skip header + next; } elsif (/^Dynamic Section:/) { $section = "dyninfo"; next; @@ -178,6 +183,12 @@ sub _parse { if ($section eq "dynsym") { $self->parse_dynamic_symbol($_); + } elsif ($section eq "dynreloc") { + if (/^\S+\s+(\S+)\s+(\S+)\s*$/) { + $self->{dynrelocs}{$2} = $1; + } else { + warning(sprintf(_g("Couldn't parse dynamic relocation record: %s"), $_)); + } } elsif ($section eq "dyninfo") { if (/^\s*NEEDED\s+(\S+)/) { push @{$self->{NEEDED}}, $1; @@ -204,6 +215,9 @@ sub _parse { } } } + # Update status of dynamic symbols given the relocations that have + # been parsed after the symbols... + $self->apply_relocations(); return $section ne "none"; } @@ -287,6 +301,18 @@ sub parse_dynamic_symbol { } } +sub apply_relocations { + my ($self) = @_; + foreach my $sym (values %{$self->{dynsyms}}) { + # We want to mark as undefined symbols those which are currently + # defined but that depend on a copy relocation + next if not $sym->{'defined'}; + next if not exists $self->{dynrelocs}{$sym->{name}}; + if ($self->{dynrelocs}{$sym->{name}} =~ /^R_.*_COPY$/) { + $sym->{'defined'} = 0; + } + } +} sub add_dynamic_symbol { my ($self, $symbol) = @_; diff --git a/scripts/t/200_Dpkg_Shlibs.t b/scripts/t/200_Dpkg_Shlibs.t index 86bdeab2..8b28ec46 100644 --- a/scripts/t/200_Dpkg_Shlibs.t +++ b/scripts/t/200_Dpkg_Shlibs.t @@ -1,6 +1,6 @@ # -*- mode: cperl;-*- -use Test::More tests => 34; +use Test::More tests => 36; use IO::String; use strict; @@ -40,6 +40,11 @@ close $objdump; ok(!$obj->is_public_library(), 'ls is not a public library'); ok($obj->is_executable(), 'ls is an executable'); +my $sym = $obj->get_symbol('optarg@GLIBC_2.0'); +ok($sym, 'optarg@GLIBC_2.0 exists'); +ok(!$sym->{'defined'}, 'R_*_COPY relocations are taken into account'); + + open $objdump, '<', "$srcdir/objdump.libc6-2.6" or die "$srcdir/objdump.libc6-2.6: $!"; $obj->reset(); @@ -57,7 +62,7 @@ is_deeply($obj->{flags}, { DYNAMIC => 1, HAS_SYMS => 1, D_PAGED => 1 }, 'flags') is_deeply($obj->{NEEDED}, [ 'ld-linux.so.2' ], 'NEEDED'); is_deeply([ $obj->get_needed_libraries ], [ 'ld-linux.so.2' ], 'NEEDED'); -my $sym = $obj->get_symbol('_sys_nerr@GLIBC_2.3'); +$sym = $obj->get_symbol('_sys_nerr@GLIBC_2.3'); is_deeply( $sym, { name => '_sys_nerr', version => 'GLIBC_2.3', soname => 'libc.so.6', section => '.rodata', dynamic => 1, debug => '', type => 'O', weak => '', diff --git a/scripts/t/200_Dpkg_Shlibs/objdump.ls b/scripts/t/200_Dpkg_Shlibs/objdump.ls index 760d87e7..f679242c 100644 --- a/scripts/t/200_Dpkg_Shlibs/objdump.ls +++ b/scripts/t/200_Dpkg_Shlibs/objdump.ls @@ -170,3 +170,108 @@ DYNAMIC SYMBOL TABLE: 0805b864 g DO .bss 00000004 GLIBC_2.0 optarg +DYNAMIC RELOCATION RECORDS +OFFSET TYPE VALUE +0805b5d4 R_386_GLOB_DAT __gmon_start__ +0805b8a0 R_386_COPY optind +0805b8a4 R_386_COPY stderr +0805b8c0 R_386_COPY stdout +0805b8c4 R_386_COPY optarg +0805b5e8 R_386_JUMP_SLOT abort +0805b5ec R_386_JUMP_SLOT __errno_location +0805b5f0 R_386_JUMP_SLOT sigemptyset +0805b5f4 R_386_JUMP_SLOT sprintf +0805b5f8 R_386_JUMP_SLOT localeconv +0805b5fc R_386_JUMP_SLOT dirfd +0805b600 R_386_JUMP_SLOT __cxa_atexit +0805b604 R_386_JUMP_SLOT strcoll +0805b608 R_386_JUMP_SLOT qsort +0805b60c R_386_JUMP_SLOT fputs_unlocked +0805b610 R_386_JUMP_SLOT __ctype_get_mb_cur_max +0805b614 R_386_JUMP_SLOT signal +0805b618 R_386_JUMP_SLOT sigismember +0805b61c R_386_JUMP_SLOT __gmon_start__ +0805b620 R_386_JUMP_SLOT realloc +0805b624 R_386_JUMP_SLOT __xstat64 +0805b628 R_386_JUMP_SLOT localtime +0805b62c R_386_JUMP_SLOT getgrnam +0805b630 R_386_JUMP_SLOT strchr +0805b634 R_386_JUMP_SLOT getenv +0805b638 R_386_JUMP_SLOT calloc +0805b63c R_386_JUMP_SLOT strncpy +0805b640 R_386_JUMP_SLOT freecon +0805b644 R_386_JUMP_SLOT memset +0805b648 R_386_JUMP_SLOT __libc_start_main +0805b64c R_386_JUMP_SLOT mempcpy +0805b650 R_386_JUMP_SLOT _obstack_begin +0805b654 R_386_JUMP_SLOT strrchr +0805b658 R_386_JUMP_SLOT chmod +0805b65c R_386_JUMP_SLOT __assert_fail +0805b660 R_386_JUMP_SLOT bindtextdomain +0805b664 R_386_JUMP_SLOT mbrtowc +0805b668 R_386_JUMP_SLOT acl_delete_def_file +0805b66c R_386_JUMP_SLOT gettimeofday +0805b670 R_386_JUMP_SLOT __ctype_toupper_loc +0805b674 R_386_JUMP_SLOT free +0805b678 R_386_JUMP_SLOT __lxstat64 +0805b67c R_386_JUMP_SLOT _obstack_newchunk +0805b680 R_386_JUMP_SLOT __overflow +0805b684 R_386_JUMP_SLOT dcgettext +0805b688 R_386_JUMP_SLOT sigaction +0805b68c R_386_JUMP_SLOT strverscmp +0805b690 R_386_JUMP_SLOT opendir +0805b694 R_386_JUMP_SLOT getopt_long +0805b698 R_386_JUMP_SLOT ioctl +0805b69c R_386_JUMP_SLOT __ctype_b_loc +0805b6a0 R_386_JUMP_SLOT iswcntrl +0805b6a4 R_386_JUMP_SLOT isatty +0805b6a8 R_386_JUMP_SLOT fclose +0805b6ac R_386_JUMP_SLOT mbsinit +0805b6b0 R_386_JUMP_SLOT _setjmp +0805b6b4 R_386_JUMP_SLOT tcgetpgrp +0805b6b8 R_386_JUMP_SLOT mktime +0805b6bc R_386_JUMP_SLOT readdir64 +0805b6c0 R_386_JUMP_SLOT memcpy +0805b6c4 R_386_JUMP_SLOT strtoul +0805b6c8 R_386_JUMP_SLOT strlen +0805b6cc R_386_JUMP_SLOT getpwuid +0805b6d0 R_386_JUMP_SLOT acl_extended_file +0805b6d4 R_386_JUMP_SLOT acl_get_file +0805b6d8 R_386_JUMP_SLOT setlocale +0805b6dc R_386_JUMP_SLOT acl_entries +0805b6e0 R_386_JUMP_SLOT strcpy +0805b6e4 R_386_JUMP_SLOT printf +0805b6e8 R_386_JUMP_SLOT raise +0805b6ec R_386_JUMP_SLOT fwrite_unlocked +0805b6f0 R_386_JUMP_SLOT clock_gettime +0805b6f4 R_386_JUMP_SLOT getfilecon +0805b6f8 R_386_JUMP_SLOT closedir +0805b6fc R_386_JUMP_SLOT fprintf +0805b700 R_386_JUMP_SLOT malloc +0805b704 R_386_JUMP_SLOT acl_set_file +0805b708 R_386_JUMP_SLOT sigprocmask +0805b70c R_386_JUMP_SLOT __fpending +0805b710 R_386_JUMP_SLOT lgetfilecon +0805b714 R_386_JUMP_SLOT error +0805b718 R_386_JUMP_SLOT getgrgid +0805b71c R_386_JUMP_SLOT __strtoull_internal +0805b720 R_386_JUMP_SLOT sigaddset +0805b724 R_386_JUMP_SLOT readlink +0805b728 R_386_JUMP_SLOT memmove +0805b72c R_386_JUMP_SLOT __ctype_tolower_loc +0805b730 R_386_JUMP_SLOT textdomain +0805b734 R_386_JUMP_SLOT __fxstat64 +0805b738 R_386_JUMP_SLOT fnmatch +0805b73c R_386_JUMP_SLOT strncmp +0805b740 R_386_JUMP_SLOT vfprintf +0805b744 R_386_JUMP_SLOT acl_free +0805b748 R_386_JUMP_SLOT fflush_unlocked +0805b74c R_386_JUMP_SLOT strftime +0805b750 R_386_JUMP_SLOT wcwidth +0805b754 R_386_JUMP_SLOT iswprint +0805b758 R_386_JUMP_SLOT getpwnam +0805b75c R_386_JUMP_SLOT strcmp +0805b760 R_386_JUMP_SLOT exit +0805b764 R_386_JUMP_SLOT acl_from_text + +