Import gdb 7.3 into vendor branch
authorJohn Marino <draco@marino.st>
Wed, 31 Aug 2011 21:22:16 +0000 (23:22 +0200)
committerJohn Marino <draco@marino.st>
Thu, 1 Sep 2011 17:43:02 +0000 (19:43 +0200)
575 files changed:
contrib/gdb-7/bfd/archive.c
contrib/gdb-7/bfd/archures.c
contrib/gdb-7/bfd/bfd-in.h
contrib/gdb-7/bfd/bfd-in2.h
contrib/gdb-7/bfd/bfd.c
contrib/gdb-7/bfd/compress.c
contrib/gdb-7/bfd/config.bfd
contrib/gdb-7/bfd/corefile.c
contrib/gdb-7/bfd/cpu-i386.c
contrib/gdb-7/bfd/dwarf2.c
contrib/gdb-7/bfd/elf-attrs.c
contrib/gdb-7/bfd/elf-bfd.h
contrib/gdb-7/bfd/elf-eh-frame.c
contrib/gdb-7/bfd/elf-ifunc.c
contrib/gdb-7/bfd/elf.c
contrib/gdb-7/bfd/elf32-i386.c
contrib/gdb-7/bfd/elf64-x86-64.c
contrib/gdb-7/bfd/elfcode.h
contrib/gdb-7/bfd/elfcore.h
contrib/gdb-7/bfd/elflink.c
contrib/gdb-7/bfd/elfxx-target.h
contrib/gdb-7/bfd/hash.c
contrib/gdb-7/bfd/libbfd.c
contrib/gdb-7/bfd/libbfd.h
contrib/gdb-7/bfd/libcoff.h
contrib/gdb-7/bfd/linker.c
contrib/gdb-7/bfd/merge.c
contrib/gdb-7/bfd/opncls.c
contrib/gdb-7/bfd/reloc.c
contrib/gdb-7/bfd/section.c
contrib/gdb-7/bfd/simple.c
contrib/gdb-7/bfd/syms.c
contrib/gdb-7/bfd/targets.c
contrib/gdb-7/bfd/version.h
contrib/gdb-7/gdb/PROBLEMS
contrib/gdb-7/gdb/ada-exp.y
contrib/gdb-7/gdb/ada-lang.c
contrib/gdb-7/gdb/ada-lang.h
contrib/gdb-7/gdb/ada-lex.c
contrib/gdb-7/gdb/ada-operator.def [new file with mode: 0644]
contrib/gdb-7/gdb/ada-tasks.c
contrib/gdb-7/gdb/ada-typeprint.c
contrib/gdb-7/gdb/ada-valprint.c
contrib/gdb-7/gdb/addrmap.c
contrib/gdb-7/gdb/addrmap.h
contrib/gdb-7/gdb/amd64-nat.c
contrib/gdb-7/gdb/amd64-nat.h
contrib/gdb-7/gdb/amd64-tdep.c
contrib/gdb-7/gdb/amd64-tdep.h
contrib/gdb-7/gdb/amd64bsd-nat.c
contrib/gdb-7/gdb/annotate.c
contrib/gdb-7/gdb/annotate.h
contrib/gdb-7/gdb/arch-utils.c
contrib/gdb-7/gdb/arch-utils.h
contrib/gdb-7/gdb/auxv.c
contrib/gdb-7/gdb/auxv.h
contrib/gdb-7/gdb/ax-gdb.c
contrib/gdb-7/gdb/ax-gdb.h
contrib/gdb-7/gdb/ax-general.c
contrib/gdb-7/gdb/ax.h
contrib/gdb-7/gdb/bcache.c
contrib/gdb-7/gdb/bcache.h
contrib/gdb-7/gdb/bfd-target.c
contrib/gdb-7/gdb/bfd-target.h
contrib/gdb-7/gdb/block.c
contrib/gdb-7/gdb/block.h
contrib/gdb-7/gdb/blockframe.c
contrib/gdb-7/gdb/breakpoint.c
contrib/gdb-7/gdb/breakpoint.h
contrib/gdb-7/gdb/bsd-kvm.c
contrib/gdb-7/gdb/bsd-kvm.h
contrib/gdb-7/gdb/bsd-uthread.c
contrib/gdb-7/gdb/bsd-uthread.h
contrib/gdb-7/gdb/buildsym.c
contrib/gdb-7/gdb/buildsym.h
contrib/gdb-7/gdb/c-exp.y
contrib/gdb-7/gdb/c-lang.c
contrib/gdb-7/gdb/c-lang.h
contrib/gdb-7/gdb/c-typeprint.c
contrib/gdb-7/gdb/c-valprint.c
contrib/gdb-7/gdb/call-cmds.h
contrib/gdb-7/gdb/cc-with-index.sh [new file with mode: 0644]
contrib/gdb-7/gdb/charset-list.h
contrib/gdb-7/gdb/charset.c
contrib/gdb-7/gdb/charset.h
contrib/gdb-7/gdb/cli-out.c
contrib/gdb-7/gdb/cli-out.h
contrib/gdb-7/gdb/cli/cli-cmds.c
contrib/gdb-7/gdb/cli/cli-cmds.h
contrib/gdb-7/gdb/cli/cli-decode.c
contrib/gdb-7/gdb/cli/cli-decode.h
contrib/gdb-7/gdb/cli/cli-dump.c
contrib/gdb-7/gdb/cli/cli-dump.h
contrib/gdb-7/gdb/cli/cli-interp.c
contrib/gdb-7/gdb/cli/cli-logging.c
contrib/gdb-7/gdb/cli/cli-script.c
contrib/gdb-7/gdb/cli/cli-script.h
contrib/gdb-7/gdb/cli/cli-setshow.c
contrib/gdb-7/gdb/cli/cli-setshow.h
contrib/gdb-7/gdb/cli/cli-utils.c [new file with mode: 0644]
contrib/gdb-7/gdb/cli/cli-utils.h [new file with mode: 0644]
contrib/gdb-7/gdb/coff-pe-read.c
contrib/gdb-7/gdb/coff-pe-read.h
contrib/gdb-7/gdb/coffread.c
contrib/gdb-7/gdb/command.h
contrib/gdb-7/gdb/common/ax.def [new file with mode: 0644]
contrib/gdb-7/gdb/common/gdb_signals.h
contrib/gdb-7/gdb/common/i386-xstate.h
contrib/gdb-7/gdb/common/signals.c
contrib/gdb-7/gdb/complaints.c
contrib/gdb-7/gdb/complaints.h
contrib/gdb-7/gdb/completer.c
contrib/gdb-7/gdb/completer.h
contrib/gdb-7/gdb/config.in
contrib/gdb-7/gdb/configure.ac
contrib/gdb-7/gdb/configure.host
contrib/gdb-7/gdb/configure.tgt
contrib/gdb-7/gdb/copying.c
contrib/gdb-7/gdb/copyright.py [new file with mode: 0644]
contrib/gdb-7/gdb/corefile.c
contrib/gdb-7/gdb/corelow.c
contrib/gdb-7/gdb/cp-abi.c
contrib/gdb-7/gdb/cp-abi.h
contrib/gdb-7/gdb/cp-name-parser.y
contrib/gdb-7/gdb/cp-namespace.c
contrib/gdb-7/gdb/cp-support.c
contrib/gdb-7/gdb/cp-support.h
contrib/gdb-7/gdb/cp-valprint.c
contrib/gdb-7/gdb/d-lang.c
contrib/gdb-7/gdb/d-lang.h
contrib/gdb-7/gdb/d-valprint.c
contrib/gdb-7/gdb/data-directory/Makefile.in [new file with mode: 0644]
contrib/gdb-7/gdb/dbxread.c
contrib/gdb-7/gdb/dcache.c
contrib/gdb-7/gdb/dcache.h
contrib/gdb-7/gdb/defs.h
contrib/gdb-7/gdb/demangle.c
contrib/gdb-7/gdb/dfp.c
contrib/gdb-7/gdb/dfp.h
contrib/gdb-7/gdb/dictionary.c
contrib/gdb-7/gdb/dictionary.h
contrib/gdb-7/gdb/disasm.c
contrib/gdb-7/gdb/disasm.h
contrib/gdb-7/gdb/doc/LRS [new file with mode: 0644]
contrib/gdb-7/gdb/doc/a4rc.sed [new file with mode: 0644]
contrib/gdb-7/gdb/doc/agentexpr.texi
contrib/gdb-7/gdb/doc/all-cfg.texi
contrib/gdb-7/gdb/doc/annotate.texinfo
contrib/gdb-7/gdb/doc/gdb.texinfo
contrib/gdb-7/gdb/doc/gdbint.texinfo
contrib/gdb-7/gdb/doc/observer.texi
contrib/gdb-7/gdb/doc/stabs.texinfo
contrib/gdb-7/gdb/doublest.c
contrib/gdb-7/gdb/doublest.h
contrib/gdb-7/gdb/dummy-frame.c
contrib/gdb-7/gdb/dummy-frame.h
contrib/gdb-7/gdb/dwarf2-frame.c
contrib/gdb-7/gdb/dwarf2-frame.h
contrib/gdb-7/gdb/dwarf2expr.c
contrib/gdb-7/gdb/dwarf2expr.h
contrib/gdb-7/gdb/dwarf2loc.c
contrib/gdb-7/gdb/dwarf2loc.h
contrib/gdb-7/gdb/dwarf2read.c
contrib/gdb-7/gdb/elfread.c
contrib/gdb-7/gdb/environ.c
contrib/gdb-7/gdb/environ.h
contrib/gdb-7/gdb/eval.c
contrib/gdb-7/gdb/event-loop.c
contrib/gdb-7/gdb/event-loop.h
contrib/gdb-7/gdb/event-top.c
contrib/gdb-7/gdb/event-top.h
contrib/gdb-7/gdb/exceptions.c
contrib/gdb-7/gdb/exceptions.h
contrib/gdb-7/gdb/exec.c
contrib/gdb-7/gdb/exec.h
contrib/gdb-7/gdb/expprint.c
contrib/gdb-7/gdb/expression.h
contrib/gdb-7/gdb/f-exp.y
contrib/gdb-7/gdb/f-lang.c
contrib/gdb-7/gdb/f-lang.h
contrib/gdb-7/gdb/f-typeprint.c
contrib/gdb-7/gdb/f-valprint.c
contrib/gdb-7/gdb/fbsd-nat.c
contrib/gdb-7/gdb/fbsd-nat.h
contrib/gdb-7/gdb/features/feature_to_c.sh
contrib/gdb-7/gdb/features/gdb-target.dtd
contrib/gdb-7/gdb/features/i386/32bit-avx.xml
contrib/gdb-7/gdb/features/i386/32bit-core.xml
contrib/gdb-7/gdb/features/i386/32bit-linux.xml
contrib/gdb-7/gdb/features/i386/32bit-sse.xml
contrib/gdb-7/gdb/features/i386/64bit-avx.xml
contrib/gdb-7/gdb/features/i386/64bit-core.xml
contrib/gdb-7/gdb/features/i386/64bit-linux.xml
contrib/gdb-7/gdb/features/i386/64bit-sse.xml
contrib/gdb-7/gdb/features/i386/amd64-avx-linux.xml
contrib/gdb-7/gdb/features/i386/amd64-avx.xml
contrib/gdb-7/gdb/features/i386/amd64-linux.xml
contrib/gdb-7/gdb/features/i386/amd64.xml
contrib/gdb-7/gdb/features/i386/i386-avx-linux.xml
contrib/gdb-7/gdb/features/i386/i386-avx.xml
contrib/gdb-7/gdb/features/i386/i386-linux.xml
contrib/gdb-7/gdb/features/i386/i386-mmx-linux.xml
contrib/gdb-7/gdb/features/i386/i386-mmx.xml
contrib/gdb-7/gdb/features/i386/i386.xml
contrib/gdb-7/gdb/features/library-list.dtd
contrib/gdb-7/gdb/features/osdata.dtd
contrib/gdb-7/gdb/features/threads.dtd
contrib/gdb-7/gdb/features/traceframe-info.dtd [new file with mode: 0644]
contrib/gdb-7/gdb/features/xinclude.dtd
contrib/gdb-7/gdb/filesystem.c
contrib/gdb-7/gdb/filesystem.h
contrib/gdb-7/gdb/findcmd.c
contrib/gdb-7/gdb/findvar.c
contrib/gdb-7/gdb/fork-child.c
contrib/gdb-7/gdb/frame-base.c
contrib/gdb-7/gdb/frame-base.h
contrib/gdb-7/gdb/frame-unwind.c
contrib/gdb-7/gdb/frame-unwind.h
contrib/gdb-7/gdb/frame.c
contrib/gdb-7/gdb/frame.h
contrib/gdb-7/gdb/gcore.c
contrib/gdb-7/gdb/gdb-gdb.py
contrib/gdb-7/gdb/gdb-stabs.h
contrib/gdb-7/gdb/gdb.1
contrib/gdb-7/gdb/gdb.c
contrib/gdb-7/gdb/gdb.h
contrib/gdb-7/gdb/gdb_assert.h
contrib/gdb-7/gdb/gdb_curses.h
contrib/gdb-7/gdb/gdb_locale.h
contrib/gdb-7/gdb/gdb_obstack.h
contrib/gdb-7/gdb/gdb_ptrace.h
contrib/gdb-7/gdb/gdb_regex.h
contrib/gdb-7/gdb/gdb_select.h
contrib/gdb-7/gdb/gdb_stat.h
contrib/gdb-7/gdb/gdb_string.h
contrib/gdb-7/gdb/gdb_thread_db.h
contrib/gdb-7/gdb/gdb_usleep.c
contrib/gdb-7/gdb/gdb_usleep.h
contrib/gdb-7/gdb/gdb_vfork.h
contrib/gdb-7/gdb/gdb_wait.h
contrib/gdb-7/gdb/gdb_wchar.h
contrib/gdb-7/gdb/gdbarch.c
contrib/gdb-7/gdb/gdbarch.h
contrib/gdb-7/gdb/gdbcmd.h
contrib/gdb-7/gdb/gdbcore.h
contrib/gdb-7/gdb/gdbthread.h
contrib/gdb-7/gdb/gdbtypes.c
contrib/gdb-7/gdb/gdbtypes.h
contrib/gdb-7/gdb/gnu-v2-abi.c
contrib/gdb-7/gdb/gnu-v3-abi.c
contrib/gdb-7/gdb/i386-nat.c
contrib/gdb-7/gdb/i386-nat.h
contrib/gdb-7/gdb/i386-tdep.c
contrib/gdb-7/gdb/i386-tdep.h
contrib/gdb-7/gdb/i386bsd-nat.c
contrib/gdb-7/gdb/i386bsd-nat.h
contrib/gdb-7/gdb/i386bsd-tdep.c
contrib/gdb-7/gdb/i386fbsd-tdep.c
contrib/gdb-7/gdb/i387-tdep.c
contrib/gdb-7/gdb/i387-tdep.h
contrib/gdb-7/gdb/inf-child.c
contrib/gdb-7/gdb/inf-child.h
contrib/gdb-7/gdb/inf-loop.c
contrib/gdb-7/gdb/inf-loop.h
contrib/gdb-7/gdb/inf-ptrace.c
contrib/gdb-7/gdb/inf-ptrace.h
contrib/gdb-7/gdb/infcall.c
contrib/gdb-7/gdb/infcall.h
contrib/gdb-7/gdb/infcmd.c
contrib/gdb-7/gdb/inferior.c
contrib/gdb-7/gdb/inferior.h
contrib/gdb-7/gdb/inflow.c
contrib/gdb-7/gdb/inflow.h
contrib/gdb-7/gdb/infrun.c
contrib/gdb-7/gdb/inline-frame.c
contrib/gdb-7/gdb/inline-frame.h
contrib/gdb-7/gdb/interps.c
contrib/gdb-7/gdb/interps.h
contrib/gdb-7/gdb/jit.c
contrib/gdb-7/gdb/jit.h
contrib/gdb-7/gdb/jv-exp.y
contrib/gdb-7/gdb/jv-lang.c
contrib/gdb-7/gdb/jv-lang.h
contrib/gdb-7/gdb/jv-typeprint.c
contrib/gdb-7/gdb/jv-valprint.c
contrib/gdb-7/gdb/language.c
contrib/gdb-7/gdb/language.h
contrib/gdb-7/gdb/linespec.c
contrib/gdb-7/gdb/linespec.h
contrib/gdb-7/gdb/m2-exp.y
contrib/gdb-7/gdb/m2-lang.c
contrib/gdb-7/gdb/m2-lang.h
contrib/gdb-7/gdb/m2-typeprint.c
contrib/gdb-7/gdb/m2-valprint.c
contrib/gdb-7/gdb/macrocmd.c
contrib/gdb-7/gdb/macroexp.c
contrib/gdb-7/gdb/macroexp.h
contrib/gdb-7/gdb/macroscope.c
contrib/gdb-7/gdb/macroscope.h
contrib/gdb-7/gdb/macrotab.c
contrib/gdb-7/gdb/macrotab.h
contrib/gdb-7/gdb/main.c
contrib/gdb-7/gdb/main.h
contrib/gdb-7/gdb/maint.c
contrib/gdb-7/gdb/mdebugread.c
contrib/gdb-7/gdb/mdebugread.h
contrib/gdb-7/gdb/mem-break.c
contrib/gdb-7/gdb/memattr.c
contrib/gdb-7/gdb/memattr.h
contrib/gdb-7/gdb/memory-map.c
contrib/gdb-7/gdb/memory-map.h
contrib/gdb-7/gdb/memrange.c [new file with mode: 0644]
contrib/gdb-7/gdb/memrange.h [new file with mode: 0644]
contrib/gdb-7/gdb/mi/mi-cmd-break.c
contrib/gdb-7/gdb/mi/mi-cmd-disas.c
contrib/gdb-7/gdb/mi/mi-cmd-env.c
contrib/gdb-7/gdb/mi/mi-cmd-file.c
contrib/gdb-7/gdb/mi/mi-cmd-stack.c
contrib/gdb-7/gdb/mi/mi-cmd-target.c
contrib/gdb-7/gdb/mi/mi-cmd-var.c
contrib/gdb-7/gdb/mi/mi-cmds.c
contrib/gdb-7/gdb/mi/mi-cmds.h
contrib/gdb-7/gdb/mi/mi-common.c
contrib/gdb-7/gdb/mi/mi-common.h
contrib/gdb-7/gdb/mi/mi-console.c
contrib/gdb-7/gdb/mi/mi-console.h
contrib/gdb-7/gdb/mi/mi-getopt.c
contrib/gdb-7/gdb/mi/mi-getopt.h
contrib/gdb-7/gdb/mi/mi-interp.c
contrib/gdb-7/gdb/mi/mi-main.c
contrib/gdb-7/gdb/mi/mi-main.h
contrib/gdb-7/gdb/mi/mi-out.c
contrib/gdb-7/gdb/mi/mi-out.h
contrib/gdb-7/gdb/mi/mi-parse.c
contrib/gdb-7/gdb/mi/mi-parse.h
contrib/gdb-7/gdb/mi/mi-symbol-cmds.c
contrib/gdb-7/gdb/minsyms.c
contrib/gdb-7/gdb/mipsread.c
contrib/gdb-7/gdb/objc-exp.y
contrib/gdb-7/gdb/objc-lang.c
contrib/gdb-7/gdb/objc-lang.h
contrib/gdb-7/gdb/objfiles.c
contrib/gdb-7/gdb/objfiles.h
contrib/gdb-7/gdb/observer.c
contrib/gdb-7/gdb/observer.sh
contrib/gdb-7/gdb/opencl-lang.c [new file with mode: 0644]
contrib/gdb-7/gdb/osabi.c
contrib/gdb-7/gdb/osabi.h
contrib/gdb-7/gdb/osdata.c
contrib/gdb-7/gdb/osdata.h
contrib/gdb-7/gdb/p-exp.y
contrib/gdb-7/gdb/p-lang.c
contrib/gdb-7/gdb/p-lang.h
contrib/gdb-7/gdb/p-typeprint.c
contrib/gdb-7/gdb/p-valprint.c
contrib/gdb-7/gdb/parse.c
contrib/gdb-7/gdb/parser-defs.h
contrib/gdb-7/gdb/posix-hdep.c
contrib/gdb-7/gdb/printcmd.c
contrib/gdb-7/gdb/proc-service.list
contrib/gdb-7/gdb/progspace.c
contrib/gdb-7/gdb/progspace.h
contrib/gdb-7/gdb/prologue-value.c
contrib/gdb-7/gdb/prologue-value.h
contrib/gdb-7/gdb/psympriv.h
contrib/gdb-7/gdb/psymtab.c
contrib/gdb-7/gdb/psymtab.h
contrib/gdb-7/gdb/python/lib/gdb/__init__.py [new file with mode: 0644]
contrib/gdb-7/gdb/python/lib/gdb/command/__init__.py [new file with mode: 0644]
contrib/gdb-7/gdb/python/lib/gdb/command/pretty_printers.py [new file with mode: 0644]
contrib/gdb-7/gdb/python/lib/gdb/printing.py [new file with mode: 0644]
contrib/gdb-7/gdb/python/lib/gdb/types.py [new file with mode: 0644]
contrib/gdb-7/gdb/python/py-auto-load.c
contrib/gdb-7/gdb/python/py-block.c [new file with mode: 0644]
contrib/gdb-7/gdb/python/py-bpevent.c [new file with mode: 0644]
contrib/gdb-7/gdb/python/py-breakpoint.c [new file with mode: 0644]
contrib/gdb-7/gdb/python/py-cmd.c [new file with mode: 0644]
contrib/gdb-7/gdb/python/py-continueevent.c [new file with mode: 0644]
contrib/gdb-7/gdb/python/py-event.c [new file with mode: 0644]
contrib/gdb-7/gdb/python/py-event.h [new file with mode: 0644]
contrib/gdb-7/gdb/python/py-events.h [new file with mode: 0644]
contrib/gdb-7/gdb/python/py-evtregistry.c [new file with mode: 0644]
contrib/gdb-7/gdb/python/py-evts.c [new file with mode: 0644]
contrib/gdb-7/gdb/python/py-exitedevent.c [new file with mode: 0644]
contrib/gdb-7/gdb/python/py-frame.c [new file with mode: 0644]
contrib/gdb-7/gdb/python/py-function.c [new file with mode: 0644]
contrib/gdb-7/gdb/python/py-inferior.c [new file with mode: 0644]
contrib/gdb-7/gdb/python/py-infthread.c [new file with mode: 0644]
contrib/gdb-7/gdb/python/py-lazy-string.c [new file with mode: 0644]
contrib/gdb-7/gdb/python/py-objfile.c [new file with mode: 0644]
contrib/gdb-7/gdb/python/py-param.c [new file with mode: 0644]
contrib/gdb-7/gdb/python/py-prettyprint.c
contrib/gdb-7/gdb/python/py-progspace.c [new file with mode: 0644]
contrib/gdb-7/gdb/python/py-signalevent.c [new file with mode: 0644]
contrib/gdb-7/gdb/python/py-stopevent.c [new file with mode: 0644]
contrib/gdb-7/gdb/python/py-stopevent.h [copied from contrib/gdb-7/gdb/mi/mi-main.h with 53% similarity]
contrib/gdb-7/gdb/python/py-symbol.c [new file with mode: 0644]
contrib/gdb-7/gdb/python/py-symtab.c [new file with mode: 0644]
contrib/gdb-7/gdb/python/py-threadevent.c [new file with mode: 0644]
contrib/gdb-7/gdb/python/py-type.c [new file with mode: 0644]
contrib/gdb-7/gdb/python/py-utils.c [new file with mode: 0644]
contrib/gdb-7/gdb/python/py-value.c
contrib/gdb-7/gdb/python/python-config.py [new file with mode: 0644]
contrib/gdb-7/gdb/python/python-internal.h [new file with mode: 0644]
contrib/gdb-7/gdb/python/python.c
contrib/gdb-7/gdb/python/python.h
contrib/gdb-7/gdb/ravenscar-sparc-thread.c [new file with mode: 0644]
contrib/gdb-7/gdb/ravenscar-thread.c [new file with mode: 0644]
contrib/gdb-7/gdb/ravenscar-thread.h [new file with mode: 0644]
contrib/gdb-7/gdb/record.c
contrib/gdb-7/gdb/record.h
contrib/gdb-7/gdb/regcache.c
contrib/gdb-7/gdb/regcache.h
contrib/gdb-7/gdb/regformats/reg-bfin.dat [new file with mode: 0644]
contrib/gdb-7/gdb/regformats/regdat.sh
contrib/gdb-7/gdb/regformats/regdef.h
contrib/gdb-7/gdb/reggroups.c
contrib/gdb-7/gdb/reggroups.h
contrib/gdb-7/gdb/regset.c
contrib/gdb-7/gdb/regset.h
contrib/gdb-7/gdb/remote-fileio.c
contrib/gdb-7/gdb/remote-fileio.h
contrib/gdb-7/gdb/remote.c
contrib/gdb-7/gdb/remote.h
contrib/gdb-7/gdb/reverse.c
contrib/gdb-7/gdb/sentinel-frame.c
contrib/gdb-7/gdb/sentinel-frame.h
contrib/gdb-7/gdb/ser-base.c
contrib/gdb-7/gdb/ser-base.h
contrib/gdb-7/gdb/ser-pipe.c
contrib/gdb-7/gdb/ser-tcp.c
contrib/gdb-7/gdb/ser-tcp.h
contrib/gdb-7/gdb/ser-unix.c
contrib/gdb-7/gdb/ser-unix.h
contrib/gdb-7/gdb/serial.c
contrib/gdb-7/gdb/serial.h
contrib/gdb-7/gdb/sim-regno.h
contrib/gdb-7/gdb/solib-svr4.c
contrib/gdb-7/gdb/solib-svr4.h
contrib/gdb-7/gdb/solib.c
contrib/gdb-7/gdb/solib.h
contrib/gdb-7/gdb/solist.h
contrib/gdb-7/gdb/source.c
contrib/gdb-7/gdb/source.h
contrib/gdb-7/gdb/stabsread.c
contrib/gdb-7/gdb/stabsread.h
contrib/gdb-7/gdb/stack.c
contrib/gdb-7/gdb/stack.h
contrib/gdb-7/gdb/std-operator.def [new file with mode: 0644]
contrib/gdb-7/gdb/std-regs.c
contrib/gdb-7/gdb/symfile.c
contrib/gdb-7/gdb/symfile.h
contrib/gdb-7/gdb/symmisc.c
contrib/gdb-7/gdb/symtab.c
contrib/gdb-7/gdb/symtab.h
contrib/gdb-7/gdb/syscalls/gdb-syscalls.dtd
contrib/gdb-7/gdb/target-descriptions.c
contrib/gdb-7/gdb/target-descriptions.h
contrib/gdb-7/gdb/target-memory.c
contrib/gdb-7/gdb/target.c
contrib/gdb-7/gdb/target.h
contrib/gdb-7/gdb/terminal.h
contrib/gdb-7/gdb/thread.c
contrib/gdb-7/gdb/top.c
contrib/gdb-7/gdb/top.h
contrib/gdb-7/gdb/tracepoint.c
contrib/gdb-7/gdb/tracepoint.h
contrib/gdb-7/gdb/trad-frame.c
contrib/gdb-7/gdb/trad-frame.h
contrib/gdb-7/gdb/tramp-frame.c
contrib/gdb-7/gdb/tramp-frame.h
contrib/gdb-7/gdb/tui/tui-command.c
contrib/gdb-7/gdb/tui/tui-command.h
contrib/gdb-7/gdb/tui/tui-data.c
contrib/gdb-7/gdb/tui/tui-data.h
contrib/gdb-7/gdb/tui/tui-disasm.c
contrib/gdb-7/gdb/tui/tui-disasm.h
contrib/gdb-7/gdb/tui/tui-file.c
contrib/gdb-7/gdb/tui/tui-file.h
contrib/gdb-7/gdb/tui/tui-hooks.c
contrib/gdb-7/gdb/tui/tui-hooks.h
contrib/gdb-7/gdb/tui/tui-interp.c
contrib/gdb-7/gdb/tui/tui-io.c
contrib/gdb-7/gdb/tui/tui-io.h
contrib/gdb-7/gdb/tui/tui-layout.c
contrib/gdb-7/gdb/tui/tui-layout.h
contrib/gdb-7/gdb/tui/tui-main.c
contrib/gdb-7/gdb/tui/tui-out.c
contrib/gdb-7/gdb/tui/tui-regs.c
contrib/gdb-7/gdb/tui/tui-regs.h
contrib/gdb-7/gdb/tui/tui-source.c
contrib/gdb-7/gdb/tui/tui-source.h
contrib/gdb-7/gdb/tui/tui-stack.c
contrib/gdb-7/gdb/tui/tui-stack.h
contrib/gdb-7/gdb/tui/tui-win.c
contrib/gdb-7/gdb/tui/tui-win.h
contrib/gdb-7/gdb/tui/tui-windata.c
contrib/gdb-7/gdb/tui/tui-windata.h
contrib/gdb-7/gdb/tui/tui-wingeneral.c
contrib/gdb-7/gdb/tui/tui-wingeneral.h
contrib/gdb-7/gdb/tui/tui-winsource.c
contrib/gdb-7/gdb/tui/tui-winsource.h
contrib/gdb-7/gdb/tui/tui.c
contrib/gdb-7/gdb/tui/tui.h
contrib/gdb-7/gdb/typeprint.c
contrib/gdb-7/gdb/typeprint.h
contrib/gdb-7/gdb/ui-file.c
contrib/gdb-7/gdb/ui-file.h
contrib/gdb-7/gdb/ui-out.c
contrib/gdb-7/gdb/ui-out.h
contrib/gdb-7/gdb/user-regs.c
contrib/gdb-7/gdb/user-regs.h
contrib/gdb-7/gdb/utils.c
contrib/gdb-7/gdb/valarith.c
contrib/gdb-7/gdb/valops.c
contrib/gdb-7/gdb/valprint.c
contrib/gdb-7/gdb/valprint.h
contrib/gdb-7/gdb/value.c
contrib/gdb-7/gdb/value.h
contrib/gdb-7/gdb/varobj.c
contrib/gdb-7/gdb/varobj.h
contrib/gdb-7/gdb/vec.c
contrib/gdb-7/gdb/vec.h
contrib/gdb-7/gdb/version.h
contrib/gdb-7/gdb/version.in
contrib/gdb-7/gdb/wrapper.c
contrib/gdb-7/gdb/wrapper.h
contrib/gdb-7/gdb/xcoffsolib.h
contrib/gdb-7/gdb/xml-support.c
contrib/gdb-7/gdb/xml-support.h
contrib/gdb-7/gdb/xml-syscall.c
contrib/gdb-7/gdb/xml-syscall.h
contrib/gdb-7/gdb/xml-tdesc.c
contrib/gdb-7/gdb/xml-tdesc.h
contrib/gdb-7/include/bfdlink.h
contrib/gdb-7/include/coff/internal.h
contrib/gdb-7/include/demangle.h
contrib/gdb-7/include/dwarf2.h
contrib/gdb-7/include/elf/common.h
contrib/gdb-7/include/elf/internal.h
contrib/gdb-7/include/elf/mips.h
contrib/gdb-7/include/filenames.h
contrib/gdb-7/include/floatformat.h
contrib/gdb-7/include/gdb/fileio.h
contrib/gdb-7/include/gdb/signals.def [new file with mode: 0644]
contrib/gdb-7/include/gdb/signals.h
contrib/gdb-7/include/gdb/sim-bfin.h [new file with mode: 0644]
contrib/gdb-7/include/libiberty.h
contrib/gdb-7/include/simple-object.h [new file with mode: 0644]
contrib/gdb-7/libdecnumber/dconfig.h
contrib/gdb-7/libiberty/argv.c
contrib/gdb-7/libiberty/concat.c
contrib/gdb-7/libiberty/cp-demangle.c
contrib/gdb-7/libiberty/cp-demangle.h
contrib/gdb-7/libiberty/cplus-dem.c
contrib/gdb-7/libiberty/filename_cmp.c
contrib/gdb-7/libiberty/floatformat.c
contrib/gdb-7/libiberty/hashtab.c
contrib/gdb-7/libiberty/lbasename.c
contrib/gdb-7/libiberty/make-relative-prefix.c
contrib/gdb-7/libiberty/make-temp-file.c
contrib/gdb-7/libiberty/pex-common.c
contrib/gdb-7/libiberty/pex-unix.c
contrib/gdb-7/libiberty/setproctitle.c [new file with mode: 0644]
contrib/gdb-7/libiberty/simple-object-coff.c [new file with mode: 0644]
contrib/gdb-7/libiberty/simple-object-common.h [new file with mode: 0644]
contrib/gdb-7/libiberty/simple-object-elf.c [new file with mode: 0644]
contrib/gdb-7/libiberty/simple-object-mach-o.c [new file with mode: 0644]
contrib/gdb-7/libiberty/simple-object.c [new file with mode: 0644]
contrib/gdb-7/libiberty/simple-object.txh [new file with mode: 0644]
contrib/gdb-7/libiberty/splay-tree.c
contrib/gdb-7/opcodes/disassemble.c
contrib/gdb-7/opcodes/i386-dis.c
contrib/gdb-7/opcodes/i386-opc.h
contrib/gdb-7/opcodes/i386-tbl.h

index fbe555b..86d07e9 100644 (file)
@@ -1,6 +1,6 @@
 /* BFD back-end for archive files (libraries).
    Copyright 1990, 1991, 1992, 1993, 1994, 1995, 1996, 1997, 1998, 1999,
-   2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010
+   2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010, 2011
    Free Software Foundation, Inc.
    Written by Cygnus Support.  Mostly Gumby Henkel-Wallace's fault.
 
@@ -348,7 +348,7 @@ _bfd_find_nested_archive (bfd *arch_bfd, const char *filename)
        abfd != NULL;
        abfd = abfd->archive_next)
     {
-      if (strcmp (filename, abfd->filename) == 0)
+      if (filename_cmp (filename, abfd->filename) == 0)
         return abfd;
     }
   abfd = bfd_openr (filename, NULL);
@@ -655,6 +655,9 @@ _bfd_get_elt_at_filepos (bfd *archive, file_ptr filepos)
 
   n_nfd->arelt_data = new_areldata;
 
+  /* Copy BFD_COMPRESS and BFD_DECOMPRESS flags.  */
+  n_nfd->flags |= archive->flags & (BFD_COMPRESS | BFD_DECOMPRESS);
+
   if (_bfd_add_bfd_to_archive_cache (archive, filepos, n_nfd))
     return n_nfd;
 
@@ -1106,6 +1109,7 @@ bfd_slurp_bsd_armap_f2 (bfd *abfd)
   struct artdata *ardata = bfd_ardata (abfd);
   char *stringbase;
   unsigned int stringsize;
+  unsigned int left;
   bfd_size_type amt;
   carsym *set;
   int i = bfd_bread (nextname, 16, abfd);
@@ -1133,43 +1137,46 @@ bfd_slurp_bsd_armap_f2 (bfd *abfd)
   if (mapdata == NULL)
     return FALSE;
 
-  amt = mapdata->parsed_size;
-  raw_armap = (bfd_byte *) bfd_zalloc (abfd, amt);
-  if (raw_armap == NULL)
+  if (mapdata->parsed_size < HPUX_SYMDEF_COUNT_SIZE + BSD_STRING_COUNT_SIZE)
     {
+    wrong_format:
+      bfd_set_error (bfd_error_wrong_format);
     byebye:
       bfd_release (abfd, mapdata);
       return FALSE;
     }
+  left = mapdata->parsed_size - HPUX_SYMDEF_COUNT_SIZE - BSD_STRING_COUNT_SIZE;
+
+  amt = mapdata->parsed_size;
+  raw_armap = (bfd_byte *) bfd_zalloc (abfd, amt);
+  if (raw_armap == NULL)
+    goto byebye;
 
   if (bfd_bread (raw_armap, amt, abfd) != amt)
     {
       if (bfd_get_error () != bfd_error_system_call)
        bfd_set_error (bfd_error_malformed_archive);
-    byebyebye:
-      bfd_release (abfd, raw_armap);
       goto byebye;
     }
 
   ardata->symdef_count = H_GET_16 (abfd, raw_armap);
 
-  if (ardata->symdef_count * BSD_SYMDEF_SIZE
-      > mapdata->parsed_size - HPUX_SYMDEF_COUNT_SIZE)
-    {
-      /* Probably we're using the wrong byte ordering.  */
-      bfd_set_error (bfd_error_wrong_format);
-      goto byebyebye;
-    }
-
   ardata->cache = 0;
 
   stringsize = H_GET_32 (abfd, raw_armap + HPUX_SYMDEF_COUNT_SIZE);
+  if (stringsize > left)
+    goto wrong_format;
+  left -= stringsize;
+
   /* Skip sym count and string sz.  */
   stringbase = ((char *) raw_armap
                + HPUX_SYMDEF_COUNT_SIZE
                + BSD_STRING_COUNT_SIZE);
   rbase = (bfd_byte *) stringbase + stringsize;
   amt = ardata->symdef_count * BSD_SYMDEF_SIZE;
+  if (amt > left)
+    goto wrong_format;
+
   ardata->symdefs = (struct carsym *) bfd_alloc (abfd, amt);
   if (!ardata->symdefs)
     return FALSE;
@@ -1213,7 +1220,9 @@ _bfd_slurp_extended_name_table (bfd *abfd)
 
   /* FIXME:  Formatting sucks here, and in case of failure of BFD_READ,
      we probably don't want to return TRUE.  */
-  bfd_seek (abfd, bfd_ardata (abfd)->first_file_filepos, SEEK_SET);
+  if (bfd_seek (abfd, bfd_ardata (abfd)->first_file_filepos, SEEK_SET) != 0)
+    return FALSE;
+
   if (bfd_bread (nextname, 16, abfd) == 16)
     {
       if (bfd_seek (abfd, (file_ptr) -16, SEEK_CUR) != 0)
@@ -1352,7 +1361,7 @@ adjust_relative_path (const char * path, const char * ref_path)
       while (*e2 && ! IS_DIR_SEPARATOR (*e2))
        ++e2;
       if (*e1 == '\0' || *e2 == '\0' || e1 - pathp != e2 - refp
-         || strncmp (pathp, refp, e1 - pathp) != 0)
+         || filename_ncmp (pathp, refp, e1 - pathp) != 0)
        break;
       pathp = e1 + 1;
       refp = e2 + 1;
@@ -1457,7 +1466,7 @@ _bfd_construct_extended_name_table (bfd *abfd,
           /* If the path is the same as the previous path seen,
              reuse it.  This can happen when flattening a thin
              archive that contains other archives.  */
-          if (last_filename && strcmp (last_filename, filename) == 0)
+          if (last_filename && filename_cmp (last_filename, filename) == 0)
             continue;
 
           last_filename = filename;
@@ -1503,7 +1512,7 @@ _bfd_construct_extended_name_table (bfd *abfd,
       else
        {
          struct ar_hdr *hdr = arch_hdr (current);
-         if (strncmp (normal, hdr->ar_name, thislen) != 0
+         if (filename_ncmp (normal, hdr->ar_name, thislen) != 0
              || (thislen < sizeof hdr->ar_name
                  && hdr->ar_name[thislen] != ar_padchar (current)))
            {
@@ -1551,7 +1560,7 @@ _bfd_construct_extended_name_table (bfd *abfd,
              archive that contains other archives.
              If the path is relative, adjust it relative to
              the containing archive.  */
-          if (last_filename && strcmp (last_filename, filename) == 0)
+          if (last_filename && filename_cmp (last_filename, filename) == 0)
             normal = last_filename;
           else if (! IS_ABSOLUTE_PATH (filename)
                    && ! IS_ABSOLUTE_PATH (abfd->filename))
@@ -1649,7 +1658,7 @@ _bfd_archive_bsd44_construct_extended_name_table (bfd *abfd,
 
           len = (len + 3) & ~3;
           arch_eltdata (current)->extra_size = len;
-          _bfd_ar_spacepad (hdr->ar_name, maxname, "#1/%u", len);
+          _bfd_ar_spacepad (hdr->ar_name, maxname, "#1/%lu", len);
        }
     }
 
@@ -2292,31 +2301,28 @@ bsd_write_armap (bfd *arch,
   bfd_byte temp[4];
   unsigned int count;
   struct ar_hdr hdr;
-  struct stat statbuf;
   long uid, gid;
 
   firstreal = mapsize + elength + sizeof (struct ar_hdr) + SARMAG;
 
-  stat (arch->filename, &statbuf);
+  /* If deterministic, we use 0 as the timestamp in the map.
+     Some linkers may require that the archive filesystem modification
+     time is less than (or near to) the archive map timestamp.  Those
+     linkers should not be used with deterministic mode.  (GNU ld and
+     Gold do not have this restriction.)  */
+  bfd_ardata (arch)->armap_timestamp = 0;
+  uid = 0;
+  gid = 0;
   if ((arch->flags & BFD_DETERMINISTIC_OUTPUT) == 0)
     {
-      /* Remember the timestamp, to keep it holy.  But fudge it a little.  */
-      bfd_ardata (arch)->armap_timestamp = (statbuf.st_mtime
-                                            + ARMAP_TIME_OFFSET);
+      struct stat statbuf;
+
+      if (stat (arch->filename, &statbuf) == 0)
+       bfd_ardata (arch)->armap_timestamp = (statbuf.st_mtime
+                                             + ARMAP_TIME_OFFSET);
       uid = getuid();
       gid = getgid();
     }
-  else
-    {
-      /* If deterministic, we use 0 as the timestamp in the map.
-         Some linkers may require that the archive filesystem modification
-         time is less than (or near to) the archive map timestamp.  Those
-         linkers should not be used with deterministic mode.  (GNU ld and
-         Gold do not have this restriction.)  */
-      bfd_ardata (arch)->armap_timestamp = 0;
-      uid = 0;
-      gid = 0;
-    }
 
   memset (&hdr, ' ', sizeof (struct ar_hdr));
   memcpy (hdr.ar_name, RANLIBMAG, strlen (RANLIBMAG));
index 0e08571..cd8500f 100644 (file)
@@ -173,6 +173,7 @@ DESCRIPTION
 .#define bfd_mach_mips5                 5
 .#define bfd_mach_mips_loongson_2e      3001
 .#define bfd_mach_mips_loongson_2f      3002
+.#define bfd_mach_mips_loongson_3a      3003
 .#define bfd_mach_mips_sb1              12310201 {* octal 'SB', 01 *}
 .#define bfd_mach_mips_octeon          6501
 .#define bfd_mach_mips_xlr              887682   {* decimal 'XLR'  *}
@@ -184,6 +185,8 @@ DESCRIPTION
 .#define bfd_mach_i386_i386 1
 .#define bfd_mach_i386_i8086 2
 .#define bfd_mach_i386_i386_intel_syntax 3
+.#define bfd_mach_x64_32 32
+.#define bfd_mach_x64_32_intel_syntax 33
 .#define bfd_mach_x86_64 64
 .#define bfd_mach_x86_64_intel_syntax 65
 .  bfd_arch_l1om,   {* Intel L1OM *}
@@ -310,7 +313,9 @@ DESCRIPTION
 .  bfd_arch_v850,      {* NEC V850 *}
 .#define bfd_mach_v850          1
 .#define bfd_mach_v850e        'E'
-.#define bfd_mach_v850e1       '1'
+.#define bfd_mach_v850e1        '1'
+.#define bfd_mach_v850e2        0x4532
+.#define bfd_mach_v850e2v3      0x45325633
 .  bfd_arch_arc,       {* ARC Cores *}
 .#define bfd_mach_arc_5         5
 .#define bfd_mach_arc_6         6
@@ -371,6 +376,13 @@ DESCRIPTION
 .#define bfd_mach_avr5         5
 .#define bfd_mach_avr51                51
 .#define bfd_mach_avr6         6
+.#define bfd_mach_avrxmega1 101
+.#define bfd_mach_avrxmega2 102
+.#define bfd_mach_avrxmega3 103
+.#define bfd_mach_avrxmega4 104
+.#define bfd_mach_avrxmega5 105
+.#define bfd_mach_avrxmega6 106
+.#define bfd_mach_avrxmega7 107
 .  bfd_arch_bfin,        {* ADI Blackfin *}
 .#define bfd_mach_bfin          1
 .  bfd_arch_cr16,       {* National Semiconductor CompactRISC (ie CR16). *}
index cfa5225..63fcdc9 100644 (file)
@@ -404,6 +404,10 @@ extern struct bfd_hash_entry *bfd_hash_lookup
 extern struct bfd_hash_entry *bfd_hash_insert
   (struct bfd_hash_table *, const char *, unsigned long);
 
+/* Rename an entry in a hash table.  */
+extern void bfd_hash_rename
+  (struct bfd_hash_table *, const char *, struct bfd_hash_entry *);
+
 /* Replace an entry in a hash table.  */
 extern void bfd_hash_replace
   (struct bfd_hash_table *, struct bfd_hash_entry *old,
index f97c67f..a1ef1c1 100644 (file)
@@ -411,6 +411,10 @@ extern struct bfd_hash_entry *bfd_hash_lookup
 extern struct bfd_hash_entry *bfd_hash_insert
   (struct bfd_hash_table *, const char *, unsigned long);
 
+/* Rename an entry in a hash table.  */
+extern void bfd_hash_rename
+  (struct bfd_hash_table *, const char *, struct bfd_hash_entry *);
+
 /* Replace an entry in a hash table.  */
 extern void bfd_hash_replace
   (struct bfd_hash_table *, struct bfd_hash_entry *old,
@@ -964,6 +968,7 @@ extern struct coff_comdat_info *bfd_coff_get_comdat_section
 void bfd_init (void);
 
 /* Extracted from opncls.c.  */
+extern unsigned int bfd_use_reserved_id;
 bfd *bfd_fopen (const char *filename, const char *target,
     const char *mode, int fd);
 
@@ -1000,6 +1005,10 @@ bfd_boolean bfd_make_writable (bfd *abfd);
 
 bfd_boolean bfd_make_readable (bfd *abfd);
 
+void *bfd_alloc (bfd *abfd, bfd_size_type wanted);
+
+void *bfd_zalloc (bfd *abfd, bfd_size_type wanted);
+
 unsigned long bfd_calc_gnu_debuglink_crc32
    (unsigned long crc, const unsigned char *buf, bfd_size_type len);
 
@@ -1348,6 +1357,12 @@ typedef struct bfd_section
   /* Mark flag used by some linker backends for garbage collection.  */
   unsigned int gc_mark : 1;
 
+  /* Section compression status.  */
+  unsigned int compress_status : 2;
+#define COMPRESS_SECTION_NONE    0
+#define COMPRESS_SECTION_DONE    1
+#define DECOMPRESS_SECTION_SIZED 2
+
   /* The following flags are used by the ELF linker. */
 
   /* Mark sections which have been allocated to segments.  */
@@ -1404,6 +1419,9 @@ typedef struct bfd_section
      section size calculated on a previous linker relaxation pass.  */
   bfd_size_type rawsize;
 
+  /* The compressed size of the section in octets.  */
+  bfd_size_type compressed_size;
+
   /* Relaxation table. */
   struct relax_table *relax;
 
@@ -1637,17 +1655,17 @@ extern asection bfd_ind_section;
   /* name, id,  index, next, prev, flags, user_set_vma,            */  \
   { NAME,  IDX, 0,     NULL, NULL, FLAGS, 0,                           \
                                                                        \
-  /* linker_mark, linker_has_input, gc_mark, segment_mark,         */  \
+  /* linker_mark, linker_has_input, gc_mark, decompress_status,    */  \
      0,           0,                1,       0,                        \
                                                                        \
-  /* sec_info_type, use_rela_p,                                    */  \
-     0,             0,                                                 \
+  /* segment_mark, sec_info_type, use_rela_p,                      */  \
+     0,            0,             0,                                   \
                                                                        \
   /* sec_flg0, sec_flg1, sec_flg2, sec_flg3, sec_flg4, sec_flg5,   */  \
      0,        0,        0,        0,        0,        0,              \
                                                                        \
-  /* vma, lma, size, rawsize, relax, relax_count,                  */  \
-     0,   0,   0,    0,       0,     0,                                \
+  /* vma, lma, size, rawsize, compressed_size, relax, relax_count, */  \
+     0,   0,   0,    0,       0,               0,     0,               \
                                                                        \
   /* output_offset, output_section,              alignment_power,  */  \
      0,             (struct bfd_section *) &SEC, 0,                    \
@@ -1699,6 +1717,9 @@ asection *bfd_make_section (bfd *, const char *name);
 bfd_boolean bfd_set_section_flags
    (bfd *abfd, asection *sec, flagword flags);
 
+void bfd_rename_section
+   (bfd *abfd, asection *sec, const char *newname);
+
 void bfd_map_over_sections
    (bfd *abfd,
     void (*func) (bfd *abfd, asection *sect, void *obj),
@@ -1839,6 +1860,7 @@ enum bfd_architecture
 #define bfd_mach_mips5                 5
 #define bfd_mach_mips_loongson_2e      3001
 #define bfd_mach_mips_loongson_2f      3002
+#define bfd_mach_mips_loongson_3a      3003
 #define bfd_mach_mips_sb1              12310201 /* octal 'SB', 01 */
 #define bfd_mach_mips_octeon           6501
 #define bfd_mach_mips_xlr              887682   /* decimal 'XLR'  */
@@ -1850,6 +1872,8 @@ enum bfd_architecture
 #define bfd_mach_i386_i386 1
 #define bfd_mach_i386_i8086 2
 #define bfd_mach_i386_i386_intel_syntax 3
+#define bfd_mach_x64_32 32
+#define bfd_mach_x64_32_intel_syntax 33
 #define bfd_mach_x86_64 64
 #define bfd_mach_x86_64_intel_syntax 65
   bfd_arch_l1om,   /* Intel L1OM */
@@ -1977,6 +2001,8 @@ enum bfd_architecture
 #define bfd_mach_v850          1
 #define bfd_mach_v850e         'E'
 #define bfd_mach_v850e1        '1'
+#define bfd_mach_v850e2        0x4532
+#define bfd_mach_v850e2v3      0x45325633
   bfd_arch_arc,       /* ARC Cores */
 #define bfd_mach_arc_5         5
 #define bfd_mach_arc_6         6
@@ -2037,6 +2063,13 @@ enum bfd_architecture
 #define bfd_mach_avr5          5
 #define bfd_mach_avr51         51
 #define bfd_mach_avr6          6
+#define bfd_mach_avrxmega1 101
+#define bfd_mach_avrxmega2 102
+#define bfd_mach_avrxmega3 103
+#define bfd_mach_avrxmega4 104
+#define bfd_mach_avrxmega5 105
+#define bfd_mach_avrxmega6 106
+#define bfd_mach_avrxmega7 107
   bfd_arch_bfin,        /* ADI Blackfin */
 #define bfd_mach_bfin          1
   bfd_arch_cr16,       /* National Semiconductor CompactRISC (ie CR16). */
@@ -3120,6 +3153,12 @@ pc-relative or some form of GOT-indirect relocation.  */
   BFD_RELOC_ARM_TLS_TPOFF32,
   BFD_RELOC_ARM_TLS_IE32,
   BFD_RELOC_ARM_TLS_LE32,
+  BFD_RELOC_ARM_TLS_GOTDESC,
+  BFD_RELOC_ARM_TLS_CALL,
+  BFD_RELOC_ARM_THM_TLS_CALL,
+  BFD_RELOC_ARM_TLS_DESCSEQ,
+  BFD_RELOC_ARM_THM_TLS_DESCSEQ,
+  BFD_RELOC_ARM_TLS_DESC,
 
 /* ARM group relocations.  */
   BFD_RELOC_ARM_ALU_PC_G0_NC,
@@ -3154,6 +3193,9 @@ pc-relative or some form of GOT-indirect relocation.  */
 /* Annotation of BX instructions.  */
   BFD_RELOC_ARM_V4BX,
 
+/* ARM support for STT_GNU_IFUNC.  */
+  BFD_RELOC_ARM_IRELATIVE,
+
 /* These relocs are only used within the ARM assembler.  They are not
 (at present) written to any object files.  */
   BFD_RELOC_ARM_IMMEDIATE,
@@ -3164,6 +3206,7 @@ pc-relative or some form of GOT-indirect relocation.  */
   BFD_RELOC_ARM_T32_ADD_PC12,
   BFD_RELOC_ARM_SHIFT_IMM,
   BFD_RELOC_ARM_SMC,
+  BFD_RELOC_ARM_HVC,
   BFD_RELOC_ARM_SWI,
   BFD_RELOC_ARM_MULTI,
   BFD_RELOC_ARM_CP_OFF_IMM,
@@ -3605,6 +3648,72 @@ bits placed non-contiguously in the instruction.  */
 instructions.  */
   BFD_RELOC_V850_LO16_SPLIT_OFFSET,
 
+/* This is a 16-bit reloc.  */
+  BFD_RELOC_V850_16_PCREL,
+
+/* This is a 17-bit reloc.  */
+  BFD_RELOC_V850_17_PCREL,
+
+/* This is a 23-bit reloc.  */
+  BFD_RELOC_V850_23,
+
+/* This is a 32-bit reloc.  */
+  BFD_RELOC_V850_32_PCREL,
+
+/* This is a 32-bit reloc.  */
+  BFD_RELOC_V850_32_ABS,
+
+/* This is a 16-bit reloc.  */
+  BFD_RELOC_V850_16_SPLIT_OFFSET,
+
+/* This is a 16-bit reloc.  */
+  BFD_RELOC_V850_16_S1,
+
+/* Low 16 bits. 16 bit shifted by 1.  */
+  BFD_RELOC_V850_LO16_S1,
+
+/* This is a 16 bit offset from the call table base pointer.  */
+  BFD_RELOC_V850_CALLT_15_16_OFFSET,
+
+/* DSO relocations.  */
+  BFD_RELOC_V850_32_GOTPCREL,
+
+/* DSO relocations.  */
+  BFD_RELOC_V850_16_GOT,
+
+/* DSO relocations.  */
+  BFD_RELOC_V850_32_GOT,
+
+/* DSO relocations.  */
+  BFD_RELOC_V850_22_PLT_PCREL,
+
+/* DSO relocations.  */
+  BFD_RELOC_V850_32_PLT_PCREL,
+
+/* DSO relocations.  */
+  BFD_RELOC_V850_COPY,
+
+/* DSO relocations.  */
+  BFD_RELOC_V850_GLOB_DAT,
+
+/* DSO relocations.  */
+  BFD_RELOC_V850_JMP_SLOT,
+
+/* DSO relocations.  */
+  BFD_RELOC_V850_RELATIVE,
+
+/* DSO relocations.  */
+  BFD_RELOC_V850_16_GOTOFF,
+
+/* DSO relocations.  */
+  BFD_RELOC_V850_32_GOTOFF,
+
+/* start code.  */
+  BFD_RELOC_V850_CODE,
+
+/* start data in text.  */
+  BFD_RELOC_V850_DATA,
+
 /* This is a 32bit pcrel reloc for the mn10300, offset by two bytes in the
 instruction.  */
   BFD_RELOC_MN10300_32_PCREL,
@@ -3665,6 +3774,10 @@ the opcode.  */
   BFD_RELOC_C6000_DSBT_INDEX,
   BFD_RELOC_C6000_PREL31,
   BFD_RELOC_C6000_COPY,
+  BFD_RELOC_C6000_JUMP_SLOT,
+  BFD_RELOC_C6000_EHTYPE,
+  BFD_RELOC_C6000_PCR_H16,
+  BFD_RELOC_C6000_PCR_L16,
   BFD_RELOC_C6000_ALIGN,
   BFD_RELOC_C6000_FPHEAD,
   BFD_RELOC_C6000_NOCMP,
@@ -3898,9 +4011,12 @@ instructions  */
   BFD_RELOC_RX_GPRELL,
   BFD_RELOC_RX_SYM,
   BFD_RELOC_RX_OP_SUBTRACT,
+  BFD_RELOC_RX_OP_NEG,
   BFD_RELOC_RX_ABS8,
   BFD_RELOC_RX_ABS16,
+  BFD_RELOC_RX_ABS16_REV,
   BFD_RELOC_RX_ABS32,
+  BFD_RELOC_RX_ABS32_REV,
   BFD_RELOC_RX_ABS16U,
   BFD_RELOC_RX_ABS16UW,
   BFD_RELOC_RX_ABS16UL,
@@ -4988,6 +5104,21 @@ struct bfd
      will be consistent from run to run.  */
 #define BFD_DETERMINISTIC_OUTPUT 0x4000
 
+  /* Compress sections in this BFD.  */
+#define BFD_COMPRESS 0x8000
+
+  /* Decompress sections in this BFD.  */
+#define BFD_DECOMPRESS 0x10000
+
+  /* Flags bits to be saved in bfd_preserve_save.  */
+#define BFD_FLAGS_SAVED \
+  (BFD_IN_MEMORY | BFD_COMPRESS | BFD_DECOMPRESS)
+
+  /* Flags bits which are for BFD use only.  */
+#define BFD_FLAGS_FOR_BFD_USE_MASK \
+  (BFD_IN_MEMORY | BFD_COMPRESS | BFD_DECOMPRESS | BFD_LINKER_CREATED \
+   | BFD_TRADITIONAL_FORMAT | BFD_DETERMINISTIC_OUTPUT)
+
   /* Currently my_archive is tested before adding origin to
      anything. I believe that this can become always an add of
      origin, with origin set to 0 for non archive files.  */
@@ -5344,6 +5475,8 @@ const char *bfd_core_file_failing_command (bfd *abfd);
 
 int bfd_core_file_failing_signal (bfd *abfd);
 
+int bfd_core_file_pid (bfd *abfd);
+
 bfd_boolean core_file_matches_executable_p
    (bfd *core_bfd, bfd *exec_bfd);
 
@@ -5540,11 +5673,13 @@ typedef struct bfd_target
 #define BFD_JUMP_TABLE_CORE(NAME) \
   NAME##_core_file_failing_command, \
   NAME##_core_file_failing_signal, \
-  NAME##_core_file_matches_executable_p
+  NAME##_core_file_matches_executable_p, \
+  NAME##_core_file_pid
 
   char *      (*_core_file_failing_command) (bfd *);
   int         (*_core_file_failing_signal) (bfd *);
   bfd_boolean (*_core_file_matches_executable_p) (bfd *, bfd *);
+  int         (*_core_file_pid) (bfd *);
 
   /* Archive entry points.  */
 #define BFD_JUMP_TABLE_ARCHIVE(NAME) \
@@ -5815,8 +5950,21 @@ bfd_byte *bfd_simple_get_relocated_section_contents
    (bfd *abfd, asection *sec, bfd_byte *outbuf, asymbol **symbol_table);
 
 /* Extracted from compress.c.  */
-bfd_boolean bfd_uncompress_section_contents
-   (bfd_byte **buffer, bfd_size_type *size);
+bfd_boolean bfd_compress_section_contents
+   (bfd *abfd, asection *section, bfd_byte *uncompressed_buffer,
+    bfd_size_type uncompressed_size);
+
+bfd_boolean bfd_get_full_section_contents
+   (bfd *abfd, asection *section, bfd_byte **ptr);
+
+bfd_boolean bfd_is_section_compressed
+   (bfd *abfd, asection *section);
+
+bfd_boolean bfd_init_section_decompress_status
+   (bfd *abfd, asection *section);
+
+bfd_boolean bfd_init_section_compress_status
+   (bfd *abfd, asection *section);
 
 #ifdef __cplusplus
 }
index 771989b..77582ec 100644 (file)
@@ -1,6 +1,6 @@
 /* Generic BFD library interface and support routines.
    Copyright 1990, 1991, 1992, 1993, 1994, 1995, 1996, 1997, 1998, 1999,
-   2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, 2009
+   2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010, 2011
    Free Software Foundation, Inc.
    Written by Cygnus Support.
 
@@ -151,6 +151,21 @@ CODE_FRAGMENT
 .     will be consistent from run to run.  *}
 .#define BFD_DETERMINISTIC_OUTPUT 0x4000
 .
+.  {* Compress sections in this BFD.  *}
+.#define BFD_COMPRESS 0x8000
+.
+.  {* Decompress sections in this BFD.  *}
+.#define BFD_DECOMPRESS 0x10000
+.
+.  {* Flags bits to be saved in bfd_preserve_save.  *}
+.#define BFD_FLAGS_SAVED \
+.  (BFD_IN_MEMORY | BFD_COMPRESS | BFD_DECOMPRESS)
+.
+.  {* Flags bits which are for BFD use only.  *}
+.#define BFD_FLAGS_FOR_BFD_USE_MASK \
+.  (BFD_IN_MEMORY | BFD_COMPRESS | BFD_DECOMPRESS | BFD_LINKER_CREATED \
+.   | BFD_TRADITIONAL_FORMAT | BFD_DETERMINISTIC_OUTPUT)
+.
 .  {* Currently my_archive is tested before adding origin to
 .     anything. I believe that this can become always an add of
 .     origin, with origin set to 0 for non archive files.  *}
@@ -508,10 +523,12 @@ DESCRIPTION
 void
 bfd_perror (const char *message)
 {
+  fflush (stdout);
   if (message == NULL || *message == '\0')
     fprintf (stderr, "%s\n", bfd_errmsg (bfd_get_error ()));
   else
     fprintf (stderr, "%s: %s\n", message, bfd_errmsg (bfd_get_error ()));
+  fflush (stderr);
 }
 
 /*
@@ -708,6 +725,7 @@ _bfd_default_error_handler (const char *fmt, ...)
   va_end (ap);
 
   putc ('\n', stderr);
+  fflush (stderr);
 }
 
 /* This is a function pointer to the routine which should handle BFD
@@ -1628,7 +1646,7 @@ bfd_preserve_save (bfd *abfd, struct bfd_preserve *preserve)
 
   abfd->tdata.any = NULL;
   abfd->arch_info = &bfd_default_arch_struct;
-  abfd->flags &= BFD_IN_MEMORY;
+  abfd->flags &= BFD_FLAGS_SAVED;
   abfd->sections = NULL;
   abfd->section_last = NULL;
   abfd->section_count = 0;
index fe1b0fd..669033c 100644 (file)
 #include <zlib.h>
 #endif
 
+#ifdef HAVE_ZLIB_H
+static bfd_boolean
+decompress_contents (bfd_byte *compressed_buffer,
+                    bfd_size_type compressed_size,
+                    bfd_byte *uncompressed_buffer,
+                    bfd_size_type uncompressed_size)
+{
+  z_stream strm;
+  int rc;
+
+  /* It is possible the section consists of several compressed
+     buffers concatenated together, so we uncompress in a loop.  */
+  strm.zalloc = NULL;
+  strm.zfree = NULL;
+  strm.opaque = NULL;
+  strm.avail_in = compressed_size - 12;
+  strm.next_in = (Bytef*) compressed_buffer + 12;
+  strm.avail_out = uncompressed_size;
+
+  rc = inflateInit (&strm);
+  while (strm.avail_in > 0)
+    {
+      if (rc != Z_OK)
+       return FALSE;
+      strm.next_out = ((Bytef*) uncompressed_buffer
+                       + (uncompressed_size - strm.avail_out));
+      rc = inflate (&strm, Z_FINISH);
+      if (rc != Z_STREAM_END)
+       return FALSE;
+      rc = inflateReset (&strm);
+    }
+  rc = inflateEnd (&strm);
+  return rc == Z_OK && strm.avail_out == 0;
+}
+#endif
+
 /*
 FUNCTION
-       bfd_uncompress_section_contents
+       bfd_compress_section_contents
 
 SYNOPSIS
-       bfd_boolean bfd_uncompress_section_contents
-         (bfd_byte **buffer, bfd_size_type *size);
+       bfd_boolean bfd_compress_section_contents
+         (bfd *abfd, asection *section, bfd_byte *uncompressed_buffer,
+          bfd_size_type uncompressed_size);
 
 DESCRIPTION
 
-       Uncompresses a section that was compressed using zlib, in place.  At
-       the call to this function, *@var{buffer} and *@var{size} should point
-       to the section contents to be uncompressed.  At the end of the
-       function, *@var{buffer} and *@var{size} will point to the uncompressed
-       contents.  This function assumes *BUFFER was allocated using
-       bfd_malloc() or equivalent.  If the section is not a valid compressed
-       section, or zlib is not installed on this machine, the input is
-       unmodified.
-
-        Returns @code{FALSE} if unable to uncompress successfully; in that case
-        the input is unmodified.  Otherwise, returns @code{TRUE}.
+       Compress data of the size specified in @var{uncompressed_size}
+       and pointed to by @var{uncompressed_buffer} using zlib and store
+       as the contents field.  This function assumes the contents
+       field was allocated using bfd_malloc() or equivalent.  If zlib
+       is not installed on this machine, the input is unmodified.
+
+       Return @code{TRUE} if the full section contents is compressed 
+       successfully.
 */
 
 bfd_boolean
-bfd_uncompress_section_contents (bfd_byte **buffer ATTRIBUTE_UNUSED,
-                                bfd_size_type *size ATTRIBUTE_UNUSED)
+bfd_compress_section_contents (bfd *abfd ATTRIBUTE_UNUSED,
+                              sec_ptr sec ATTRIBUTE_UNUSED,
+                              bfd_byte *uncompressed_buffer ATTRIBUTE_UNUSED,
+                              bfd_size_type uncompressed_size ATTRIBUTE_UNUSED)
 {
 #ifndef HAVE_ZLIB_H
+  bfd_set_error (bfd_error_invalid_operation);
   return FALSE;
 #else
-  bfd_size_type compressed_size = *size;
-  bfd_byte *compressed_buffer = *buffer;
+  uLong compressed_size;
+  bfd_byte *compressed_buffer;
+
+  compressed_size = compressBound (uncompressed_size) + 12;
+  compressed_buffer = (bfd_byte *) bfd_malloc (compressed_size);
+
+  if (compressed_buffer == NULL)
+    return FALSE;
+
+  if (compress ((Bytef*) compressed_buffer + 12,
+               &compressed_size,
+               (const Bytef*) uncompressed_buffer,
+               uncompressed_size) != Z_OK)
+    {
+      free (compressed_buffer);
+      bfd_set_error (bfd_error_bad_value);
+      return FALSE;
+    }
+
+  /* Write the zlib header.  In this case, it should be "ZLIB" followed
+     by the uncompressed section size, 8 bytes in big-endian order.  */
+  memcpy (compressed_buffer, "ZLIB", 4);
+  compressed_buffer[11] = uncompressed_size; uncompressed_size >>= 8;
+  compressed_buffer[10] = uncompressed_size; uncompressed_size >>= 8;
+  compressed_buffer[9] = uncompressed_size; uncompressed_size >>= 8;
+  compressed_buffer[8] = uncompressed_size; uncompressed_size >>= 8;
+  compressed_buffer[7] = uncompressed_size; uncompressed_size >>= 8;
+  compressed_buffer[6] = uncompressed_size; uncompressed_size >>= 8;
+  compressed_buffer[5] = uncompressed_size; uncompressed_size >>= 8;
+  compressed_buffer[4] = uncompressed_size;
+  compressed_size += 12;
+
+  /* Free the uncompressed contents if we compress in place.  */
+  if (uncompressed_buffer == sec->contents)
+    free (uncompressed_buffer);
+
+  sec->contents = compressed_buffer;
+  sec->size = compressed_size;
+  sec->compress_status = COMPRESS_SECTION_DONE;
+
+  return TRUE;
+#endif  /* HAVE_ZLIB_H */
+}
+
+/*
+FUNCTION
+       bfd_get_full_section_contents
+
+SYNOPSIS
+       bfd_boolean bfd_get_full_section_contents
+         (bfd *abfd, asection *section, bfd_byte **ptr);
+
+DESCRIPTION
+       Read all data from @var{section} in BFD @var{abfd}, decompress
+       if needed, and store in @var{*ptr}.  If @var{*ptr} is NULL,
+       return @var{*ptr} with memory malloc'd by this function.  
+
+       Return @code{TRUE} if the full section contents is retrieved
+       successfully.
+*/
+
+bfd_boolean
+bfd_get_full_section_contents (bfd *abfd, sec_ptr sec, bfd_byte **ptr)
+{
+  bfd_size_type sz = sec->rawsize ? sec->rawsize : sec->size;
+  bfd_byte *p = *ptr;
+#ifdef HAVE_ZLIB_H
+  bfd_boolean ret;
+  bfd_size_type compressed_size;
   bfd_size_type uncompressed_size;
+  bfd_size_type rawsize;
+  bfd_byte *compressed_buffer;
   bfd_byte *uncompressed_buffer;
-  z_stream strm;
-  int rc;
-  bfd_size_type header_size = 12;
+#endif
+
+  if (sz == 0)
+    return TRUE;
+
+  switch (sec->compress_status)
+    {
+    case COMPRESS_SECTION_NONE:
+      if (p == NULL)
+       {
+         p = (bfd_byte *) bfd_malloc (sz);
+         if (p == NULL)
+           return FALSE;
+       }
+      if (!bfd_get_section_contents (abfd, sec, p, 0, sz))
+       {
+         if (*ptr != p)
+           free (p);
+         return FALSE;
+       }
+      *ptr = p;
+      return TRUE;
+
+    case DECOMPRESS_SECTION_SIZED:
+#ifndef HAVE_ZLIB_H
+      bfd_set_error (bfd_error_invalid_operation);
+      return FALSE;
+#else
+      /* Read in the full compressed section contents.  */
+      uncompressed_size = sec->size;
+      compressed_size = sec->compressed_size;
+      compressed_buffer = (bfd_byte *) bfd_malloc (compressed_size);
+      if (compressed_buffer == NULL)
+       return FALSE;
+      rawsize = sec->rawsize;
+      /* Clear rawsize, set size to compressed size and set compress_status
+        to COMPRESS_SECTION_NONE.  If the compressed size is bigger than
+        the uncompressed size, bfd_get_section_contents will fail.  */
+      sec->rawsize = 0;
+      sec->size = compressed_size;
+      sec->compress_status = COMPRESS_SECTION_NONE;
+      ret = bfd_get_section_contents (abfd, sec, compressed_buffer,
+                                     0, compressed_size);
+      /* Restore rawsize and size.  */
+      sec->rawsize = rawsize;
+      sec->size = uncompressed_size;
+      sec->compress_status = DECOMPRESS_SECTION_SIZED;
+      if (!ret)
+       goto fail_compressed;
+
+      uncompressed_buffer = (bfd_byte *) bfd_malloc (uncompressed_size);
+      if (uncompressed_buffer == NULL)
+       goto fail_compressed;
+
+      if (!decompress_contents (compressed_buffer, compressed_size,
+                               uncompressed_buffer, uncompressed_size))
+       {
+         bfd_set_error (bfd_error_bad_value);
+         free (uncompressed_buffer);
+       fail_compressed:
+         free (compressed_buffer);
+         return FALSE;
+       }
+
+      free (compressed_buffer);
+      sec->contents = uncompressed_buffer;
+      sec->compress_status = COMPRESS_SECTION_DONE;
+      /* Fall thru */
+#endif
+
+    case COMPRESS_SECTION_DONE:
+      if (p == NULL)
+       {
+         p = (bfd_byte *) bfd_malloc (sz);
+         if (p == NULL)
+           return FALSE;
+         *ptr = p;
+       }
+      memcpy (p, sec->contents, sz);
+      return TRUE;
+
+    default:
+      abort ();
+    }
+}
+
+/*
+FUNCTION
+       bfd_is_section_compressed
+
+SYNOPSIS
+       bfd_boolean bfd_is_section_compressed
+         (bfd *abfd, asection *section);
+
+DESCRIPTION
+       Return @code{TRUE} if @var{section} is compressed.
+*/
+
+bfd_boolean
+bfd_is_section_compressed (bfd *abfd, sec_ptr sec)
+{
+  bfd_byte compressed_buffer [12];
 
   /* Read the zlib header.  In this case, it should be "ZLIB" followed
      by the uncompressed section size, 8 bytes in big-endian order.  */
-  if (compressed_size < header_size
-      || ! CONST_STRNEQ ((char*) compressed_buffer, "ZLIB"))
-    return FALSE;
+  return (bfd_get_section_contents (abfd, sec, compressed_buffer, 0, 12)
+         && CONST_STRNEQ ((char*) compressed_buffer, "ZLIB"));
+}
+
+/*
+FUNCTION
+       bfd_init_section_decompress_status
+
+SYNOPSIS
+       bfd_boolean bfd_init_section_decompress_status
+         (bfd *abfd, asection *section);
+
+DESCRIPTION
+       Record compressed section size, update section size with
+       decompressed size and set compress_status to
+       DECOMPRESS_SECTION_SIZED.
+
+       Return @code{FALSE} if the section is not a valid compressed
+       section or zlib is not installed on this machine.  Otherwise,
+       return @code{TRUE}.
+*/
+
+bfd_boolean
+bfd_init_section_decompress_status (bfd *abfd ATTRIBUTE_UNUSED,
+                                   sec_ptr sec ATTRIBUTE_UNUSED)
+{
+#ifndef HAVE_ZLIB_H
+  bfd_set_error (bfd_error_invalid_operation);
+  return FALSE;
+#else
+  bfd_byte compressed_buffer [12];
+  bfd_size_type uncompressed_size;
+
+  if (sec->rawsize != 0
+      || sec->contents != NULL
+      || sec->compress_status != COMPRESS_SECTION_NONE
+      || !bfd_get_section_contents (abfd, sec, compressed_buffer, 0, 12))
+    {
+      bfd_set_error (bfd_error_invalid_operation);
+      return FALSE;
+    }
+
+  /* Read the zlib header.  In this case, it should be "ZLIB" followed
+     by the uncompressed section size, 8 bytes in big-endian order.  */
+  if (! CONST_STRNEQ ((char*) compressed_buffer, "ZLIB"))
+    {
+      bfd_set_error (bfd_error_wrong_format);
+      return FALSE;
+    }
+
   uncompressed_size = compressed_buffer[4]; uncompressed_size <<= 8;
   uncompressed_size += compressed_buffer[5]; uncompressed_size <<= 8;
   uncompressed_size += compressed_buffer[6]; uncompressed_size <<= 8;
@@ -79,42 +331,66 @@ bfd_uncompress_section_contents (bfd_byte **buffer ATTRIBUTE_UNUSED,
   uncompressed_size += compressed_buffer[10]; uncompressed_size <<= 8;
   uncompressed_size += compressed_buffer[11];
 
-  /* It is possible the section consists of several compressed
-     buffers concatenated together, so we uncompress in a loop.  */
-  strm.zalloc = NULL;
-  strm.zfree = NULL;
-  strm.opaque = NULL;
-  strm.avail_in = compressed_size - header_size;
-  strm.next_in = (Bytef*) compressed_buffer + header_size;
-  strm.avail_out = uncompressed_size;
-  uncompressed_buffer = (bfd_byte *) bfd_malloc (uncompressed_size);
-  if (! uncompressed_buffer)
-    return FALSE;
+  sec->compressed_size = sec->size;
+  sec->size = uncompressed_size;
+  sec->compress_status = DECOMPRESS_SECTION_SIZED;
 
-  rc = inflateInit (&strm);
-  while (strm.avail_in > 0)
+  return TRUE;
+#endif
+}
+
+/*
+FUNCTION
+       bfd_init_section_compress_status
+
+SYNOPSIS
+       bfd_boolean bfd_init_section_compress_status
+         (bfd *abfd, asection *section);
+
+DESCRIPTION
+       If open for read, compress section, update section size with
+       compressed size and set compress_status to COMPRESS_SECTION_DONE.
+
+       Return @code{FALSE} if the section is not a valid compressed
+       section or zlib is not installed on this machine.  Otherwise,
+       return @code{TRUE}.
+*/
+
+bfd_boolean
+bfd_init_section_compress_status (bfd *abfd ATTRIBUTE_UNUSED,
+                                 sec_ptr sec ATTRIBUTE_UNUSED)
+{
+#ifndef HAVE_ZLIB_H
+  bfd_set_error (bfd_error_invalid_operation);
+  return FALSE;
+#else
+  bfd_size_type uncompressed_size;
+  bfd_byte *uncompressed_buffer;
+  bfd_boolean ret;
+
+  /* Error if not opened for read.  */
+  if (abfd->direction != read_direction
+      || sec->size == 0
+      || sec->rawsize != 0
+      || sec->contents != NULL
+      || sec->compress_status != COMPRESS_SECTION_NONE)
     {
-      if (rc != Z_OK)
-        goto fail;
-      strm.next_out = ((Bytef*) uncompressed_buffer
-                       + (uncompressed_size - strm.avail_out));
-      rc = inflate (&strm, Z_FINISH);
-      if (rc != Z_STREAM_END)
-        goto fail;
-      rc = inflateReset (&strm);
+      bfd_set_error (bfd_error_invalid_operation);
+      return FALSE;
     }
-  rc = inflateEnd (&strm);
-  if (rc != Z_OK
-      || strm.avail_out != 0)
-    goto fail;
 
-  free (compressed_buffer);
-  *buffer = uncompressed_buffer;
-  *size = uncompressed_size;
-  return TRUE;
+  /* Read in the full section contents and compress it.  */
+  uncompressed_size = sec->size;
+  uncompressed_buffer = (bfd_byte *) bfd_malloc (uncompressed_size);
+  if (!bfd_get_section_contents (abfd, sec, uncompressed_buffer,
+                                0, uncompressed_size))
+    ret = FALSE;
+  else
+    ret = bfd_compress_section_contents (abfd, sec,
+                                        uncompressed_buffer,
+                                        uncompressed_size);
 
- fail:
   free (uncompressed_buffer);
-  return FALSE;
-#endif  /* HAVE_ZLIB_H */
+  return ret;
+#endif
 }
index 1015f3c..76d1927 100644 (file)
@@ -418,7 +418,7 @@ case "${targ}" in
     targ_selvecs=bfd_elf32_frv_vec
     ;;
 
-  moxie-*-elf | moxie-*-uclinux)
+  moxie-*-elf | moxie-*-rtems | moxie-*-uclinux)
     targ_defvec=bfd_elf32_moxie_vec
     ;;
 
@@ -551,13 +551,17 @@ case "${targ}" in
     targ_defvec=i386bsd_vec
     targ_underscore=yes
     ;;
+  i[3-7]86-*-dragonfly*)
+    targ_defvec=bfd_elf32_i386_vec
+    targ64_selvecs="bfd_elf64_x86_64_vec bfd_elf64_l1om_vec"
+    ;;
   i[3-7]86-*-freebsdaout* | i[3-7]86-*-freebsd[12].* | \
   i[3-7]86-*-freebsd[12])
     targ_defvec=i386freebsd_vec
     targ_selvecs=i386bsd_vec
     targ_underscore=yes
     ;;
-  i[3-7]86-*-freebsd* | i[3-7]86-*-kfreebsd*-gnu | i[3-7]86-*-dragonfly*)
+  i[3-7]86-*-freebsd* | i[3-7]86-*-kfreebsd*-gnu)
     targ_defvec=bfd_elf32_i386_freebsd_vec
     targ_selvecs="bfd_elf32_i386_vec i386pei_vec i386coff_vec"
     targ64_selvecs="bfd_elf64_x86_64_freebsd_vec bfd_elf64_x86_64_vec x86_64pei_vec bfd_elf64_l1om_vec bfd_elf64_l1om_freebsd_vec"
@@ -598,7 +602,7 @@ case "${targ}" in
   i[3-7]86-*-linux-*)
     targ_defvec=bfd_elf32_i386_vec
     targ_selvecs="i386linux_vec i386pei_vec"
-    targ64_selvecs="bfd_elf64_x86_64_vec bfd_elf64_l1om_vec"
+    targ64_selvecs="bfd_elf64_x86_64_vec bfd_elf32_x86_64_vec bfd_elf64_l1om_vec"
     ;;
 #ifdef BFD64
   x86_64-*-darwin*)
@@ -617,6 +621,11 @@ case "${targ}" in
     targ_selvecs="bfd_elf32_i386_vec bfd_elf64_l1om_vec i386coff_vec"
     want64=true
     ;;
+  x86_64-*-dragonfly*)
+    targ_defvec=bfd_elf64_x86_64_vec
+    targ_selvecs="bfd_elf32_i386_vec bfd_elf64_l1om_vec"
+    want64=true
+    ;;
   x86_64-*-freebsd* | x86_64-*-kfreebsd*-gnu)
     targ_defvec=bfd_elf64_x86_64_freebsd_vec
     targ_selvecs="bfd_elf32_i386_freebsd_vec i386coff_vec i386pei_vec x86_64pei_vec bfd_elf32_i386_vec bfd_elf64_x86_64_vec bfd_elf64_l1om_vec bfd_elf64_l1om_freebsd_vec"
@@ -629,12 +638,12 @@ case "${targ}" in
     ;;
   x86_64-*-linux-*)
     targ_defvec=bfd_elf64_x86_64_vec
-    targ_selvecs="bfd_elf32_i386_vec i386linux_vec i386pei_vec x86_64pei_vec bfd_elf64_l1om_vec"
+    targ_selvecs="bfd_elf32_i386_vec bfd_elf32_x86_64_vec i386linux_vec i386pei_vec x86_64pei_vec bfd_elf64_l1om_vec"
     want64=true
     ;;
   x86_64-*-mingw*)
     targ_defvec=x86_64pe_vec
-    targ_selvecs="x86_64pe_vec x86_64pei_vec bfd_elf64_x86_64_vec bfd_elf64_l1om_vec"
+    targ_selvecs="x86_64pe_vec x86_64pei_vec bfd_elf64_x86_64_vec bfd_elf64_l1om_vec i386pe_vec i386pei_vec bfd_elf32_i386_vec"
     want64=true
     targ_underscore=no
     ;;
@@ -1015,6 +1024,40 @@ case "${targ}" in
     targ_selvecs="bfd_elf32_tradlittlemips_vec ecoff_big_vec ecoff_little_vec bfd_elf32_ntradbigmips_vec bfd_elf64_tradbigmips_vec bfd_elf32_ntradlittlemips_vec bfd_elf64_tradlittlemips_vec"
     want64=true
     ;;
+#ifdef BFD64
+  mips64*el-*-freebsd* | mips64*el-*-kfreebsd*-gnu)
+    # FreeBSD vectors
+    targ_defvec=bfd_elf32_ntradlittlemips_freebsd_vec
+    targ_selvecs="bfd_elf32_ntradbigmips_freebsd_vec bfd_elf32_tradlittlemips_freebsd_vec bfd_elf32_tradbigmips_freebsd_vec bfd_elf64_tradlittlemips_freebsd_vec bfd_elf64_tradbigmips_freebsd_vec"
+    # Generic vectors
+    targ_selvecs="${targ_selvecs} bfd_elf32_ntradlittlemips_vec bfd_elf32_ntradbigmips_vec bfd_elf32_tradlittlemips_vec bfd_elf32_tradbigmips_vec bfd_elf64_tradlittlemips_vec bfd_elf64_tradbigmips_vec"
+    want64=true
+    ;;
+  mips64*-*-freebsd* | mips64*-*-kfreebsd*-gnu)
+    # FreeBSD vectors
+    targ_defvec=bfd_elf32_ntradbigmips_freebsd_vec
+    targ_selvecs="bfd_elf32_ntradlittlemips_freebsd_vec bfd_elf32_tradbigmips_freebsd_vec bfd_elf32_tradlittlemips_freebsd_vec bfd_elf64_tradbigmips_freebsd_vec bfd_elf64_tradlittlemips_freebsd_vec"
+    # Generic vectors
+    targ_selvecs="${targ_selvecs} bfd_elf32_ntradbigmips_vec bfd_elf32_ntradlittlemips_vec bfd_elf32_tradbigmips_vec bfd_elf32_tradlittlemips_vec bfd_elf64_tradbigmips_vec bfd_elf64_tradlittlemips_vec"
+    want64=true
+    ;;
+#endif
+  mips*el-*-freebsd* | mips*el-*-kfreebsd*-gnu)
+    # FreeBSD vectors
+    targ_defvec=bfd_elf32_tradlittlemips_freebsd_vec
+    targ_selvecs="bfd_elf32_tradbigmips_freebsd_vec bfd_elf32_ntradlittlemips_freebsd_vec bfd_elf64_tradlittlemips_freebsd_vec bfd_elf32_ntradbigmips_freebsd_vec bfd_elf64_tradbigmips_freebsd_vec"
+    # Generic vectors
+    targ_selvecs="${targ_selvecs} bfd_elf32_tradlittlemips_vec bfd_elf32_tradbigmips_vec bfd_elf32_ntradlittlemips_vec bfd_elf64_tradlittlemips_vec bfd_elf32_ntradbigmips_vec bfd_elf64_tradbigmips_vec"
+    want64=true
+    ;;
+  mips*-*-freebsd* | mips*-*-kfreebsd*-gnu)
+    # FreeBSD vectors
+    targ_defvec=bfd_elf32_tradbigmips_freebsd_vec
+    targ_selvecs="bfd_elf32_tradlittlemips_freebsd_vec bfd_elf32_ntradbigmips_freebsd_vec bfd_elf64_tradbigmips_freebsd_vec bfd_elf32_ntradlittlemips_freebsd_vec bfd_elf64_tradlittlemips_freebsd_vec"
+    # Generic vectors
+    targ_selvecs="${targ_selvecs} bfd_elf32_tradbigmips_vec bfd_elf32_tradlittlemips_vec bfd_elf32_ntradbigmips_vec bfd_elf64_tradbigmips_vec bfd_elf32_ntradlittlemips_vec bfd_elf64_tradlittlemips_vec"
+    want64=true
+    ;;
 #ifdef BFD64
   mmix-*-*)
     targ_defvec=bfd_elf64_mmix_vec
@@ -1076,26 +1119,26 @@ case "${targ}" in
     targ_selvecs="bfd_elf32_pjl_vec bfd_elf32_pj_vec bfd_elf32_i386_vec"
     ;;
 
-  powerpc-*-aix5.[01])
+  powerpc-*-aix5.[01] | rs6000-*-aix5.[01])
     targ_defvec=rs6000coff_vec
     targ_selvecs="aix5coff64_vec"
     want64=true
     ;;
 #ifdef BFD64
-  powerpc64-*-aix5.[01])
+  powerpc64-*-aix5.[01] | rs6000-*-aix5.[01])
     targ_defvec=aix5coff64_vec
     targ_selvecs="rs6000coff_vec"
     want64=true
     ;;
 #endif
-  powerpc-*-aix[5-9]*)
+  powerpc-*-aix[5-9]* | rs6000-*-aix[5-9]*)
     targ_cflags=-DAIX_WEAK_SUPPORT
     targ_defvec=rs6000coff_vec
     targ_selvecs="aix5coff64_vec"
     want64=true
     ;;
 #ifdef BFD64
-  powerpc64-*-aix[5-9]*)
+  powerpc64-*-aix[5-9]* | rs6000-*-aix[5-9]*)
     targ_cflags=-DAIX_WEAK_SUPPORT
     targ_defvec=aix5coff64_vec
     targ_selvecs="rs6000coff_vec"
@@ -1122,12 +1165,12 @@ case "${targ}" in
   powerpc64-*-elf* | powerpc-*-elf64* | powerpc64-*-linux* | \
   powerpc64-*-*bsd*)
     targ_defvec=bfd_elf64_powerpc_vec
-    targ_selvecs="bfd_elf64_powerpcle_vec bfd_elf32_powerpc_vec bfd_elf32_powerpcle_vec rs6000coff_vec rs6000coff64_vec"
+    targ_selvecs="bfd_elf64_powerpcle_vec bfd_elf32_powerpc_vec bfd_elf32_powerpcle_vec rs6000coff_vec rs6000coff64_vec aix5coff64_vec"
     want64=true
     ;;
   powerpc64le-*-elf* | powerpcle-*-elf64*)
     targ_defvec=bfd_elf64_powerpcle_vec
-    targ_selvecs="bfd_elf64_powerpc_vec bfd_elf32_powerpcle_vec bfd_elf32_powerpc_vec rs6000coff_vec rs6000coff64_vec"
+    targ_selvecs="bfd_elf64_powerpc_vec bfd_elf32_powerpcle_vec bfd_elf32_powerpc_vec rs6000coff_vec rs6000coff64_vec aix5coff64_vec"
     want64=true
     ;;
 #endif
@@ -1395,14 +1438,18 @@ case "${targ}" in
     targ_defvec=bfd_elf32_sparc_vec
     targ_selvecs=sparcnetbsd_vec
     ;;
-  sparc-*-elf* | sparc-*-solaris2.[0-6] | sparc-*-solaris2.[0-6].*)
+  sparc-*-elf*)
     targ_defvec=bfd_elf32_sparc_vec
     targ_selvecs=sunos_big_vec
     ;;
+  sparc-*-solaris2.[0-6] | sparc-*-solaris2.[0-6].*)
+    targ_defvec=bfd_elf32_sparc_sol2_vec
+    targ_selvecs=sunos_big_vec
+    ;;
 #ifdef BFD64
   sparc-*-solaris2* | sparcv9-*-solaris2* | sparc64-*-solaris2*)
-    targ_defvec=bfd_elf32_sparc_vec
-    targ_selvecs="bfd_elf64_sparc_vec sunos_big_vec"
+    targ_defvec=bfd_elf32_sparc_sol2_vec
+    targ_selvecs="bfd_elf64_sparc_sol2_vec sunos_big_vec"
     want64=true
     ;;
 #endif
@@ -1428,7 +1475,7 @@ case "${targ}" in
     targ_selvecs="bfd_elf32_sparc_vec sparclinux_vec sunos_big_vec"
     want64=true
     ;;
-  sparc64-*-elf*)
+  sparc64-*-elf* | sparc64-*-rtems* )
     targ_defvec=bfd_elf64_sparc_vec
     targ_selvecs=bfd_elf32_sparc_vec
     want64=true
@@ -1437,7 +1484,7 @@ case "${targ}" in
   sparc*-*-coff*)
     targ_defvec=sparccoff_vec
     ;;
-  sparc*-*-rtems*)
+  sparc-*-rtems*)
     targ_defvec=bfd_elf32_sparc_vec
     targ_selvecs="sunos_big_vec sparccoff_vec"
     ;;
@@ -1458,7 +1505,7 @@ case "${targ}" in
     ;;
 #endif
 
-  tic6x-*-elf)
+  tic6x-*-*)
     targ_defvec=bfd_elf32_tic6x_le_vec
     targ_selvecs=bfd_elf32_tic6x_be_vec
     ;;
@@ -1468,13 +1515,7 @@ case "${targ}" in
     targ_underscore=yes
     ;;
 
-  v850-*-*)
-    targ_defvec=bfd_elf32_v850_vec
-    ;;
-  v850e-*-*)
-    targ_defvec=bfd_elf32_v850_vec
-    ;;
-  v850ea-*-*)
+  v850*-*-*)
     targ_defvec=bfd_elf32_v850_vec
     ;;
 
index 7802a3a..bba0d1c 100644 (file)
@@ -82,6 +82,31 @@ bfd_core_file_failing_signal (bfd *abfd)
   return BFD_SEND (abfd, _core_file_failing_signal, (abfd));
 }
 
+/*
+FUNCTION
+       bfd_core_file_pid
+
+SYNOPSIS
+       int bfd_core_file_pid (bfd *abfd);
+
+DESCRIPTION
+
+       Returns the PID of the process the core dump the BFD
+       @var{abfd} is attached to was generated from.
+*/
+
+int
+bfd_core_file_pid (bfd *abfd)
+{
+  if (abfd->format != bfd_core)
+    {
+      bfd_set_error (bfd_error_invalid_operation);
+      return 0;
+    }
+  return BFD_SEND (abfd, _core_file_pid, (abfd));
+}
+
+
 /*
 FUNCTION
        core_file_matches_executable_p
@@ -161,6 +186,6 @@ generic_core_file_matches_executable_p (bfd *core_bfd, bfd *exec_bfd)
   if (last_slash != NULL)
     exec = last_slash + 1;
   
-  return strcmp (exec, core) == 0;
+  return filename_cmp (exec, core) == 0;
 }
 
index 44cca9d..c4f41c5 100644 (file)
@@ -1,6 +1,6 @@
 /* BFD support for the Intel 386 architecture.
    Copyright 1992, 1994, 1995, 1996, 1998, 2000, 2001, 2002, 2004, 2005,
-   2007, 2009
+   2007, 2009, 2010, 2011
    Free Software Foundation, Inc.
 
    This file is part of BFD, the Binary File Descriptor library.
 #include "bfd.h"
 #include "libbfd.h"
 
+static const bfd_arch_info_type *
+bfd_i386_compatible (const bfd_arch_info_type *a,
+                    const bfd_arch_info_type *b)
+{
+  const bfd_arch_info_type *compat = bfd_default_compatible (a, b);
+
+  /* Don't allow mixing x64_32 with x86_64.  */
+  if (compat && a->bits_per_address != b->bits_per_address)
+    compat = NULL;
+
+  return compat;
+}
+
+static const bfd_arch_info_type bfd_x64_32_arch_intel_syntax =
+{
+  64, /* 64 bits in a word */
+  32, /* 32 bits in an address */
+  8,  /* 8 bits in a byte */
+  bfd_arch_i386,
+  bfd_mach_x64_32_intel_syntax,
+  "i386:intel",
+  "i386:x64-32:intel",
+  3,
+  FALSE,
+  bfd_i386_compatible,
+  bfd_default_scan,
+  0
+};
+
 static const bfd_arch_info_type bfd_x86_64_arch_intel_syntax =
 {
   64, /* 64 bits in a word */
@@ -35,9 +64,9 @@ static const bfd_arch_info_type bfd_x86_64_arch_intel_syntax =
   "i386:x86-64:intel",
   3,
   FALSE,
-  bfd_default_compatible,
+  bfd_i386_compatible,
   bfd_default_scan,
-  0
+  &bfd_x64_32_arch_intel_syntax,
 };
 
 static const bfd_arch_info_type bfd_i386_arch_intel_syntax =
@@ -51,7 +80,7 @@ static const bfd_arch_info_type bfd_i386_arch_intel_syntax =
   "i386:intel",
   3,
   TRUE,
-  bfd_default_compatible,
+  bfd_i386_compatible,
   bfd_default_scan,
   &bfd_x86_64_arch_intel_syntax
 };
@@ -67,11 +96,27 @@ static const bfd_arch_info_type i8086_arch =
   "i8086",
   3,
   FALSE,
-  bfd_default_compatible,
+  bfd_i386_compatible,
   bfd_default_scan,
   &bfd_i386_arch_intel_syntax
 };
 
+static const bfd_arch_info_type bfd_x64_32_arch =
+{
+  64, /* 64 bits in a word */
+  32, /* 32 bits in an address */
+  8,  /* 8 bits in a byte */
+  bfd_arch_i386,
+  bfd_mach_x64_32,
+  "i386",
+  "i386:x64-32",
+  3,
+  FALSE,
+  bfd_i386_compatible,
+  bfd_default_scan,
+  &i8086_arch
+};
+
 static const bfd_arch_info_type bfd_x86_64_arch =
 {
   64, /* 64 bits in a word */
@@ -83,9 +128,9 @@ static const bfd_arch_info_type bfd_x86_64_arch =
   "i386:x86-64",
   3,
   FALSE,
-  bfd_default_compatible,
+  bfd_i386_compatible,
   bfd_default_scan,
-  &i8086_arch
+  &bfd_x64_32_arch
 };
 
 const bfd_arch_info_type bfd_i386_arch =
@@ -99,7 +144,7 @@ const bfd_arch_info_type bfd_i386_arch =
   "i386",
   3,
   TRUE,
-  bfd_default_compatible,
+  bfd_i386_compatible,
   bfd_default_scan,
   &bfd_x86_64_arch
 };
index 6983a1c..3826856 100644 (file)
@@ -275,6 +275,60 @@ struct attr_abbrev
   enum dwarf_form form;
 };
 
+/* Map of uncompressed DWARF debug section name to compressed one.  It
+   is terminated by NULL uncompressed_name.  */
+
+struct dwarf_debug_section dwarf_debug_sections[] =
+{
+  { ".debug_abbrev",           ".zdebug_abbrev" },
+  { ".debug_aranges",          ".zdebug_aranges" },
+  { ".debug_frame",            ".zdebug_frame" },
+  { ".debug_info",             ".zdebug_info" },
+  { ".debug_line",             ".zdebug_line" },
+  { ".debug_loc",              ".zdebug_loc" },
+  { ".debug_macinfo",          ".zdebug_macinfo" },
+  { ".debug_pubnames",         ".zdebug_pubnames" },
+  { ".debug_pubtypes",         ".zdebug_pubtypes" },
+  { ".debug_ranges",           ".zdebug_ranges" },
+  { ".debug_static_func",      ".zdebug_static_func" },
+  { ".debug_static_vars",      ".zdebug_static_vars" },
+  { ".debug_str",              ".zdebug_str", },
+  { ".debug_types",            ".zdebug_types" },
+  /* GNU DWARF 1 extensions */
+  { ".debug_sfnames",          ".zdebug_sfnames" },
+  { ".debug_srcinfo",          ".zebug_srcinfo" },
+  /* SGI/MIPS DWARF 2 extensions */
+  { ".debug_funcnames",                ".zdebug_funcnames" },
+  { ".debug_typenames",                ".zdebug_typenames" },
+  { ".debug_varnames",         ".zdebug_varnames" },
+  { ".debug_weaknames",                ".zdebug_weaknames" },
+  { NULL,                      NULL },
+};
+
+enum dwarf_debug_section_enum
+{
+  debug_abbrev = 0,
+  debug_aranges,
+  debug_frame,
+  debug_info,
+  debug_line,
+  debug_loc,
+  debug_macinfo,
+  debug_pubnames,
+  debug_pubtypes,
+  debug_ranges,
+  debug_static_func,
+  debug_static_vars,
+  debug_str,
+  debug_types,
+  debug_sfnames,
+  debug_srcinfo,
+  debug_funcnames,
+  debug_typenames,
+  debug_varnames,
+  debug_weaknames
+};
+
 #ifndef ABBREV_HASH_SIZE
 #define ABBREV_HASH_SIZE 121
 #endif
@@ -405,54 +459,6 @@ lookup_info_hash_table (struct info_hash_table *hash_table, const char *key)
   return entry ? entry->head : NULL;
 }
 
-/* Read a section, uncompress it if necessary, and relocate it.  */
-
-static bfd_boolean
-read_and_uncompress_section (bfd *           abfd,
-                            asection *      msec,
-                            bfd_boolean     section_is_compressed,
-                            asymbol **      syms,
-                            bfd_byte **     section_buffer,
-                            bfd_size_type * section_size)
-{
-  /* Get the unrelocated contents of the section.  */
-  *section_buffer = (bfd_byte *) bfd_malloc (*section_size);
-  if (! *section_buffer)
-    return FALSE;
-  if (! bfd_get_section_contents (abfd, msec, *section_buffer,
-                                 0, *section_size))
-    return FALSE;
-
-  if (section_is_compressed)
-    {
-      if (! bfd_uncompress_section_contents (section_buffer, section_size))
-       {
-         (*_bfd_error_handler) (_("Dwarf Error: unable to decompress %s section."),
-                                bfd_get_section_name (abfd, msec));
-         bfd_set_error (bfd_error_bad_value);
-         return FALSE;
-       }
-    }
-
-  if (syms)
-    {
-      /* We want to relocate the data we've already read (and
-        decompressed), so we store a pointer to the data in
-        the bfd_section, and tell it that the contents are
-        already in memory.  */
-      BFD_ASSERT (msec->contents == NULL && (msec->flags & SEC_IN_MEMORY) == 0);
-      msec->contents = *section_buffer;
-      msec->flags |= SEC_IN_MEMORY;
-      msec->size = *section_size;
-      *section_buffer
-         = bfd_simple_get_relocated_section_contents (abfd, msec, NULL, syms);
-      if (! *section_buffer)
-       return FALSE;
-    }
-
-  return TRUE;
-}
-
 /* Read a section into its appropriate place in the dwarf2_debug
    struct (indicated by SECTION_BUFFER and SECTION_SIZE).  If SYMS is
    not NULL, use bfd_simple_get_relocated_section_contents to read the
@@ -461,24 +467,23 @@ read_and_uncompress_section (bfd *           abfd,
 
 static bfd_boolean
 read_section (bfd *           abfd,
-             const char *    section_name,
-             const char *    compressed_section_name,
+             enum dwarf_debug_section_enum sec,
              asymbol **      syms,
              bfd_uint64_t    offset,
              bfd_byte **     section_buffer,
              bfd_size_type * section_size)
 {
   asection *msec;
-  bfd_boolean section_is_compressed = FALSE;
+  const char *section_name = dwarf_debug_sections[sec].uncompressed_name;
 
   /* read_section is a noop if the section has already been read.  */
   if (!*section_buffer)
     {
       msec = bfd_get_section_by_name (abfd, section_name);
-      if (! msec && compressed_section_name)
+      if (! msec)
        {
-         msec = bfd_get_section_by_name (abfd, compressed_section_name);
-         section_is_compressed = TRUE;
+         section_name = dwarf_debug_sections[sec].compressed_name;
+         msec = bfd_get_section_by_name (abfd, section_name);
        }
       if (! msec)
        {
@@ -488,10 +493,22 @@ read_section (bfd *           abfd,
        }
 
       *section_size = msec->rawsize ? msec->rawsize : msec->size;
-
-      if (! read_and_uncompress_section (abfd, msec, section_is_compressed,
-                                        syms, section_buffer, section_size))
-       return FALSE;
+      if (syms)
+       {
+         *section_buffer
+             = bfd_simple_get_relocated_section_contents (abfd, msec, NULL, syms);
+         if (! *section_buffer)
+           return FALSE;
+       }
+      else
+       {
+         *section_buffer = (bfd_byte *) bfd_malloc (*section_size);
+         if (! *section_buffer)
+           return FALSE;
+         if (! bfd_get_section_contents (abfd, msec, *section_buffer,
+                                         0, *section_size))
+           return FALSE;
+       }
     }
 
   /* It is possible to get a bad value for the offset into the section
@@ -587,8 +604,7 @@ read_indirect_string (struct comp_unit * unit,
 
   *bytes_read_ptr = unit->offset_size;
 
-  if (! read_section (unit->abfd, ".debug_str", ".zdebug_str",
-                     stash->syms, offset,
+  if (! read_section (unit->abfd, debug_str, stash->syms, offset,
                      &stash->dwarf_str_buffer, &stash->dwarf_str_size))
     return NULL;
 
@@ -670,8 +686,7 @@ read_abbrevs (bfd *abfd, bfd_uint64_t offset, struct dwarf2_debug *stash)
   unsigned int abbrev_form, hash_number;
   bfd_size_type amt;
 
-  if (! read_section (abfd, ".debug_abbrev", ".zdebug_abbrev",
-                     stash->syms, offset,
+  if (! read_section (abfd, debug_abbrev, stash->syms, offset,
                      &stash->dwarf_abbrev_buffer, &stash->dwarf_abbrev_size))
     return NULL;
 
@@ -1379,8 +1394,7 @@ decode_line_info (struct comp_unit *unit, struct dwarf2_debug *stash)
   unsigned char op_code, extended_op, adj_opcode;
   bfd_size_type amt;
 
-  if (! read_section (abfd, ".debug_line", ".zdebug_line",
-                     stash->syms, unit->line_offset,
+  if (! read_section (abfd, debug_line, stash->syms, unit->line_offset,
                      &stash->dwarf_line_buffer, &stash->dwarf_line_size))
     return NULL;
 
@@ -1795,8 +1809,7 @@ static bfd_boolean
 read_debug_ranges (struct comp_unit *unit)
 {
   struct dwarf2_debug *stash = unit->stash;
-  return read_section (unit->abfd, ".debug_ranges", ".zdebug_ranges",
-                      stash->syms, 0,
+  return read_section (unit->abfd, debug_ranges, stash->syms, 0,
                       &stash->dwarf_ranges_buffer, &stash->dwarf_ranges_size);
 }
 
@@ -2135,7 +2148,7 @@ scan_unit_for_symbols (struct comp_unit *unit)
        {
          info_ptr = read_attribute (&attr, &abbrev->attrs[i], unit, info_ptr);
          if (info_ptr == NULL)
-           return FALSE;
+           goto fail;
 
          if (func)
            {
@@ -3218,80 +3231,37 @@ find_line (bfd *abfd,
        {
          /* Case 1: only one info section.  */
          total_size = msec->size;
-         if (! read_section (debug_bfd, ".debug_info", ".zdebug_info",
-                             symbols, 0,
+         if (! read_section (debug_bfd, debug_info, symbols, 0,
                              &stash->info_ptr_memory, &total_size))
            goto done;
        }
       else
        {
-         int all_uncompressed = 1;
+         /* Case 2: multiple sections.  */
          for (total_size = 0; msec; msec = find_debug_info (debug_bfd, msec))
-           {
-             total_size += msec->size;
-             if (strcmp (msec->name, DWARF2_COMPRESSED_DEBUG_INFO) == 0)
-               all_uncompressed = 0;
-           }
-         if (all_uncompressed)
-           {
-             /* Case 2: multiple sections, but none is compressed.  */
-             stash->info_ptr_memory = (bfd_byte *) bfd_malloc (total_size);
-             if (stash->info_ptr_memory == NULL)
-               goto done;
+           total_size += msec->size;
 
-             total_size = 0;
-             for (msec = find_debug_info (debug_bfd, NULL);
-                  msec;
-                  msec = find_debug_info (debug_bfd, msec))
-               {
-                 bfd_size_type size;
+         stash->info_ptr_memory = (bfd_byte *) bfd_malloc (total_size);
+         if (stash->info_ptr_memory == NULL)
+           goto done;
 
-                 size = msec->size;
-                 if (size == 0)
-                   continue;
+         total_size = 0;
+         for (msec = find_debug_info (debug_bfd, NULL);
+              msec;
+              msec = find_debug_info (debug_bfd, msec))
+           {
+             bfd_size_type size;
 
-                 if (!(bfd_simple_get_relocated_section_contents
-                       (debug_bfd, msec, stash->info_ptr_memory + total_size,
-                        symbols)))
-                   goto done;
+             size = msec->size;
+             if (size == 0)
+               continue;
 
-                 total_size += size;
-               }
-           }
-         else
-           {
-             /* Case 3: multiple sections, some or all compressed.  */
-             stash->info_ptr_memory = NULL;
-             total_size = 0;
-             for (msec = find_debug_info (debug_bfd, NULL);
-                  msec;
-                  msec = find_debug_info (debug_bfd, msec))
-               {
-                 bfd_size_type size = msec->size;
-                 bfd_byte *buffer, *tmp;
-                 bfd_boolean is_compressed =
-                     strcmp (msec->name, DWARF2_COMPRESSED_DEBUG_INFO) == 0;
-
-                 if (size == 0)
-                   continue;
-
-                 if (! read_and_uncompress_section (debug_bfd, msec,
-                                                    is_compressed, symbols,
-                                                    &buffer, &size))
-                   goto done;
-
-                 tmp = (bfd_byte *) bfd_realloc (stash->info_ptr_memory,
-                                                 total_size + size);
-                 if (tmp == NULL)
-                   {
-                     free (buffer);
-                     goto done;
-                   }
-                 stash->info_ptr_memory = tmp;
-                 memcpy (stash->info_ptr_memory + total_size, buffer, size);
-                 free (buffer);
-                 total_size += size;
-               }
+             if (!(bfd_simple_get_relocated_section_contents
+                   (debug_bfd, msec, stash->info_ptr_memory + total_size,
+                    symbols)))
+               goto done;
+
+             total_size += size;
            }
        }
 
index b9d3bf2..569e846 100644 (file)
@@ -586,3 +586,114 @@ _bfd_elf_merge_object_attributes (bfd *ibfd, bfd *obfd)
 
   return TRUE;
 }
+
+/* Merge an unknown processor-specific attribute TAG, within the range
+   of known attributes, from IBFD into OBFD; return TRUE if the link
+   is OK, FALSE if it must fail.  */
+
+bfd_boolean
+_bfd_elf_merge_unknown_attribute_low (bfd *ibfd, bfd *obfd, int tag)
+{
+  obj_attribute *in_attr;
+  obj_attribute *out_attr;
+  bfd *err_bfd = NULL;
+  bfd_boolean result = TRUE;
+
+  in_attr = elf_known_obj_attributes_proc (ibfd);
+  out_attr = elf_known_obj_attributes_proc (obfd);
+
+  if (out_attr[tag].i != 0 || out_attr[tag].s != NULL)
+    err_bfd = obfd;
+  else if (in_attr[tag].i != 0 || in_attr[tag].s != NULL)
+    err_bfd = ibfd;
+
+  if (err_bfd != NULL)
+    result
+      = get_elf_backend_data (err_bfd)->obj_attrs_handle_unknown (err_bfd, tag);
+
+  /* Only pass on attributes that match in both inputs.  */
+  if (in_attr[tag].i != out_attr[tag].i
+      || (in_attr[tag].s == NULL) != (out_attr[tag].s == NULL)
+      || (in_attr[tag].s != NULL && out_attr[tag].s != NULL
+         && strcmp (in_attr[tag].s, out_attr[tag].s) != 0))
+    {
+      out_attr[tag].i = 0;
+      out_attr[tag].s = NULL;
+    }
+
+  return result;
+}
+
+/* Merge the lists of unknown processor-specific attributes, outside
+   the known range, from IBFD into OBFD; return TRUE if the link is
+   OK, FALSE if it must fail.  */
+
+bfd_boolean
+_bfd_elf_merge_unknown_attribute_list (bfd *ibfd, bfd *obfd)
+{
+  obj_attribute_list *in_list;
+  obj_attribute_list *out_list;
+  obj_attribute_list **out_listp;
+  bfd_boolean result = TRUE;
+
+  in_list = elf_other_obj_attributes_proc (ibfd);
+  out_listp = &elf_other_obj_attributes_proc (obfd);
+  out_list = *out_listp;
+
+  for (; in_list || out_list; )
+    {
+      bfd *err_bfd = NULL;
+      int err_tag = 0;
+
+      /* The tags for each list are in numerical order.  */
+      /* If the tags are equal, then merge.  */
+      if (out_list && (!in_list || in_list->tag > out_list->tag))
+       {
+         /* This attribute only exists in obfd.  We can't merge, and we don't
+            know what the tag means, so delete it.  */
+         err_bfd = obfd;
+         err_tag = out_list->tag;
+         *out_listp = out_list->next;
+         out_list = *out_listp;
+       }
+      else if (in_list && (!out_list || in_list->tag < out_list->tag))
+       {
+         /* This attribute only exists in ibfd. We can't merge, and we don't
+            know what the tag means, so ignore it.  */
+         err_bfd = ibfd;
+         err_tag = in_list->tag;
+         in_list = in_list->next;
+       }
+      else /* The tags are equal.  */
+       {
+         /* As present, all attributes in the list are unknown, and
+            therefore can't be merged meaningfully.  */
+         err_bfd = obfd;
+         err_tag = out_list->tag;
+
+         /*  Only pass on attributes that match in both inputs.  */
+         if (in_list->attr.i != out_list->attr.i
+             || (in_list->attr.s == NULL) != (out_list->attr.s == NULL)
+             || (in_list->attr.s && out_list->attr.s
+                 && strcmp (in_list->attr.s, out_list->attr.s) != 0))
+           {
+             /* No match.  Delete the attribute.  */
+             *out_listp = out_list->next;
+             out_list = *out_listp;
+           }
+         else
+           {
+             /* Matched.  Keep the attribute and move to the next.  */
+             out_list = out_list->next;
+             in_list = in_list->next;
+           }
+       }
+
+      if (err_bfd)
+       result = result
+         && get_elf_backend_data (err_bfd)->obj_attrs_handle_unknown (err_bfd,
+                                                                      err_tag);
+    }
+
+  return result;
+}
index 754e733..21ec38f 100644 (file)
@@ -153,6 +153,9 @@ struct elf_link_hash_entry
   /* Symbol st_other value, symbol visibility.  */
   unsigned int other : 8;
 
+  /* The symbol's st_target_internal value (see Elf_Internal_Sym).  */
+  unsigned int target_internal : 8;
+
   /* Symbol is referenced by a non-shared object (other than the object
      in which it is defined).  */
   unsigned int ref_regular : 1;
@@ -689,6 +692,10 @@ struct elf_backend_data
   /* The architecture for this backend.  */
   enum bfd_architecture arch;
 
+  /* An identifier used to distinguish different target specific
+     extensions to elf_obj_tdata and elf_link_hash_table structures.  */
+  enum elf_target_id target_id;
+
   /* The ELF machine code (EM_xxxx) for this backend.  */
   int elf_machine_code;
 
@@ -1252,6 +1259,13 @@ struct elf_backend_data
      actual tag number to place in the input position.  */
   int (*obj_attrs_order) (int);
 
+  /* Handle merging unknown attributes; either warn and return TRUE,
+     or give an error and return FALSE.  */
+  bfd_boolean (*obj_attrs_handle_unknown) (bfd *, int);
+
+  /* This is non-zero if static TLS segments require a special alignment.  */
+  unsigned static_tls_alignment;
+
   /* This is TRUE if the linker should act like collect and gather
      global constructors and destructors by name.  This is TRUE for
      MIPS ELF because the Irix 5 tools can not handle the .init
@@ -1315,6 +1329,23 @@ struct elf_backend_data
   unsigned default_execstack : 1;
 };
 
+/* Information about reloc sections associated with a bfd_elf_section_data
+   structure.  */
+struct bfd_elf_section_reloc_data
+{
+  /* The ELF header for the reloc section associated with this
+     section, if any.  */
+  Elf_Internal_Shdr *hdr;
+  /* The number of relocations currently assigned to HDR.  */
+  unsigned int count;
+  /* The ELF section number of the reloc section.  Only used for an
+     output file.  */
+  int idx;
+  /* Used by the backend linker to store the symbol hash table entries
+     associated with relocs against global symbols.  */
+  struct elf_link_hash_entry **hashes;
+};
+
 /* Information stored for each BFD section in an ELF file.  This
    structure is allocated by elf_new_section_hook.  */
 
@@ -1323,31 +1354,13 @@ struct bfd_elf_section_data
   /* The ELF header for this section.  */
   Elf_Internal_Shdr this_hdr;
 
-  /* The ELF header for the reloc section associated with this
-     section, if any.  */
-  Elf_Internal_Shdr rel_hdr;
-
-  /* If there is a second reloc section associated with this section,
-     as can happen on Irix 6, this field points to the header.  */
-  Elf_Internal_Shdr *rel_hdr2;
-
-  /* The number of relocations currently assigned to REL_HDR.  */
-  unsigned int rel_count;
-
-  /* The number of relocations currently assigned to REL_HDR2.  */
-  unsigned int rel_count2;
+  /* Information about the REL and RELA reloc sections associated
+     with this section, if any.  */
+  struct bfd_elf_section_reloc_data rel, rela;
 
   /* The ELF section number of this section.  */
   int this_idx;
 
-  /* The ELF section number of the reloc section indicated by
-     REL_HDR if any.  Only used for an output file.  */
-  int rel_idx;
-
-  /* The ELF section number of the reloc section indicated by
-     REL_HDR2 if any.  Only used for an output file.  */
-  int rel_idx2;
-
   /* Used by the backend linker when generating a shared library to
      record the dynamic symbol index for a section symbol
      corresponding to this section.  A value of 0 means that there is
@@ -1357,10 +1370,6 @@ struct bfd_elf_section_data
   /* A pointer to the linked-to section for SHF_LINK_ORDER.  */
   asection *linked_to;
 
-  /* Used by the backend linker to store the symbol hash table entries
-     associated with relocs against global symbols.  */
-  struct elf_link_hash_entry **rel_hashes;
-
   /* A pointer to the swapped relocs.  If the section uses REL relocs,
      rather than RELA, all the r_addend fields will be zero.  This
      pointer may be NULL.  It is used by the backend linker.  */
@@ -1739,7 +1748,7 @@ extern bfd_reloc_status_type bfd_elf_generic_reloc
   (bfd *, arelent *, asymbol *, void *, asection *, bfd *, char **);
 extern bfd_boolean bfd_elf_allocate_object
   (bfd *, size_t, enum elf_target_id);
-extern bfd_boolean bfd_elf_make_generic_object
+extern bfd_boolean bfd_elf_make_object
   (bfd *);
 extern bfd_boolean bfd_elf_mkcorefile
   (bfd *);
@@ -1848,7 +1857,7 @@ extern int _bfd_elf_sizeof_headers
 extern bfd_boolean _bfd_elf_new_section_hook
   (bfd *, asection *);
 extern bfd_boolean _bfd_elf_init_reloc_shdr
-  (bfd *, Elf_Internal_Shdr *, asection *, bfd_boolean);
+  (bfd *, struct bfd_elf_section_reloc_data *, asection *, bfd_boolean);
 extern const struct bfd_elf_special_section *_bfd_elf_get_special_section
   (const char *, const struct bfd_elf_special_section *, unsigned int);
 extern const struct bfd_elf_special_section *_bfd_elf_get_sec_type_attr
@@ -1989,6 +1998,8 @@ extern int bfd_elf32_core_file_failing_signal
   (bfd *);
 extern bfd_boolean bfd_elf32_core_file_matches_executable_p
   (bfd *, bfd *);
+extern int bfd_elf32_core_file_pid
+  (bfd *);
 
 extern bfd_boolean bfd_elf32_swap_symbol_in
   (bfd *, const void *, const void *, Elf_Internal_Sym *);
@@ -2033,6 +2044,8 @@ extern int bfd_elf64_core_file_failing_signal
   (bfd *);
 extern bfd_boolean bfd_elf64_core_file_matches_executable_p
   (bfd *, bfd *);
+extern int bfd_elf64_core_file_pid
+  (bfd *);
 
 extern bfd_boolean bfd_elf64_swap_symbol_in
   (bfd *, const void *, const void *, Elf_Internal_Sym *);
@@ -2229,6 +2242,9 @@ extern void _bfd_elf_copy_obj_attributes (bfd *, bfd *);
 extern int _bfd_elf_obj_attrs_arg_type (bfd *, int, int);
 extern void _bfd_elf_parse_attributes (bfd *, Elf_Internal_Shdr *);
 extern bfd_boolean _bfd_elf_merge_object_attributes (bfd *, bfd *);
+extern bfd_boolean _bfd_elf_merge_unknown_attribute_low (bfd *, bfd *, int);
+extern bfd_boolean _bfd_elf_merge_unknown_attribute_list (bfd *, bfd *);
+extern Elf_Internal_Shdr *_bfd_elf_single_rel_hdr (asection *sec);
 
 /* The linker may needs to keep track of the number of relocs that it
    decides to copy as dynamic relocs in check_relocs for each symbol.
@@ -2259,6 +2275,14 @@ extern bfd_boolean _bfd_elf_allocate_ifunc_dyn_relocs
   (struct bfd_link_info *, struct elf_link_hash_entry *,
    struct elf_dyn_relocs **, unsigned int, unsigned int);
 
+extern void elf_append_rela (bfd *, asection *, Elf_Internal_Rela *);
+extern void elf_append_rel (bfd *, asection *, Elf_Internal_Rela *);
+
+extern bfd_vma elf64_r_info (bfd_vma, bfd_vma);
+extern bfd_vma elf64_r_sym (bfd_vma);
+extern bfd_vma elf32_r_info (bfd_vma, bfd_vma);
+extern bfd_vma elf32_r_sym (bfd_vma);
+
 /* Large common section.  */
 extern asection _bfd_elf_large_com_section;
 
@@ -2348,6 +2372,9 @@ extern asection _bfd_elf_large_com_section;
 #define RELOC_AGAINST_DISCARDED_SECTION(info, input_bfd, input_section,        \
                                        rel, relend, howto, contents)   \
   {                                                                    \
+    _bfd_clear_contents (howto, input_bfd, input_section,              \
+                        contents + rel->r_offset);                     \
+                                                                       \
     if (info->relocatable                                              \
        && (input_section->flags & SEC_DEBUGGING))                      \
       {                                                                        \
@@ -2355,13 +2382,13 @@ extern asection _bfd_elf_large_com_section;
           sections may require relocations.  */                        \
        Elf_Internal_Shdr *rel_hdr;                                     \
                                                                        \
-       rel_hdr = &elf_section_data (input_section->output_section)->rel_hdr; \
+       rel_hdr = _bfd_elf_single_rel_hdr (input_section->output_section); \
                                                                        \
        /* Avoid empty output section.  */                              \
        if (rel_hdr->sh_size > rel_hdr->sh_entsize)                     \
          {                                                             \
            rel_hdr->sh_size -= rel_hdr->sh_entsize;                    \
-           rel_hdr = &elf_section_data (input_section)->rel_hdr;       \
+           rel_hdr = _bfd_elf_single_rel_hdr (input_section);          \
            rel_hdr->sh_size -= rel_hdr->sh_entsize;                    \
                                                                        \
            memmove (rel, rel + 1, (relend - rel) * sizeof (*rel));     \
@@ -2373,7 +2400,6 @@ extern asection _bfd_elf_large_com_section;
          }                                                             \
       }                                                                        \
                                                                        \
-    _bfd_clear_contents (howto, input_bfd, contents + rel->r_offset);  \
     rel->r_info = 0;                                                   \
     rel->r_addend = 0;                                                 \
     continue;                                                          \
index 8380ef8..0a22138 100644 (file)
@@ -1572,10 +1572,31 @@ _bfd_elf_write_section_eh_frame (bfd *abfd,
                  break;
                case DW_EH_PE_datarel:
                  {
-                   asection *got = bfd_get_section_by_name (abfd, ".got");
-
-                   BFD_ASSERT (got != NULL);
-                   address += got->vma;
+                   switch (abfd->arch_info->arch)
+                     {
+                     case bfd_arch_ia64:
+                       BFD_ASSERT (elf_gp (abfd) != 0);
+                       address += elf_gp (abfd);
+                       break;
+                     default:
+                       (*info->callbacks->einfo)
+                         (_("%P: DW_EH_PE_datarel unspecified"
+                            " for this architecture.\n"));
+                       /* Fall thru */
+                     case bfd_arch_frv:
+                     case bfd_arch_i386:
+                       BFD_ASSERT (htab->hgot != NULL
+                                   && ((htab->hgot->root.type
+                                        == bfd_link_hash_defined)
+                                       || (htab->hgot->root.type
+                                           == bfd_link_hash_defweak)));
+                       address
+                         += (htab->hgot->root.u.def.value
+                             + htab->hgot->root.u.def.section->output_offset
+                             + (htab->hgot->root.u.def.section->output_section
+                                ->vma));
+                       break;
+                     }
                  }
                  break;
                case DW_EH_PE_pcrel:
@@ -1596,6 +1617,11 @@ _bfd_elf_write_section_eh_frame (bfd *abfd,
 
          if (hdr_info)
            {
+             /* The address calculation may overflow, giving us a
+                value greater than 4G on a 32-bit target when
+                dwarf_vma is 64-bit.  */
+             if (sizeof (address) > 4 && ptr_size == 4)
+               address &= 0xffffffff;
              hdr_info->array[hdr_info->array_count].initial_loc = address;
              hdr_info->array[hdr_info->array_count++].fde
                = (sec->output_section->vma
index 0de236f..81429b8 100644 (file)
@@ -187,6 +187,29 @@ _bfd_elf_allocate_ifunc_dyn_relocs (struct bfd_link_info *info,
 
   htab = elf_hash_table (info);
 
+  /* Support garbage collection against STT_GNU_IFUNC symbols.  */
+  if (h->plt.refcount <= 0 && h->got.refcount <= 0)
+    {
+      /* When building shared library, we need to handle the case
+         where it is marked with regular reference, but not non-GOT
+        reference.  It may happen if we didn't see STT_GNU_IFUNC
+        symbol at the time when checking relocations.  */
+      if (info->shared
+         && !h->non_got_ref
+         && h->ref_regular)
+       for (p = *head; p != NULL; p = p->next)
+         if (p->count)
+           {
+             h->non_got_ref = 1;
+             goto keep;
+           }
+
+      h->got = htab->init_got_offset;
+      h->plt = htab->init_plt_offset;
+      *head = NULL;
+      return TRUE;
+    }
+
   /* Return and discard space for dynamic relocations against it if
      it is never referenced in a non-shared object.  */
   if (!h->ref_regular)
@@ -200,6 +223,7 @@ _bfd_elf_allocate_ifunc_dyn_relocs (struct bfd_link_info *info,
       return TRUE;
     }
 
+keep:
   bed = get_elf_backend_data (info->output_bfd);
   if (bed->rela_plts_and_copies_p)
     sizeof_reloc = bed->s->sizeof_rela;
@@ -249,10 +273,20 @@ _bfd_elf_allocate_ifunc_dyn_relocs (struct bfd_link_info *info,
     *head = NULL;
 
   /* Finally, allocate space.  */
-  for (p = *head; p != NULL; p = p->next)
-    htab->irelifunc->size += p->count * sizeof_reloc;
+  p = *head;
+  if (p != NULL)
+    {
+      bfd_size_type count = 0;
+      do
+       {
+         count += p->count;
+         p = p->next;
+       }
+      while (p != NULL);
+      htab->irelifunc->size += count * sizeof_reloc;
+    }
 
-  /* For STT_GNU_IFUNC symbol, .got.plt has the real function addres
+  /* For STT_GNU_IFUNC symbol, .got.plt has the real function address
      and .got has the PLT entry adddress.  We will load the GOT entry
      with the PLT entry in finish_dynamic_symbol if it is used.  For
      branch, it uses .got.plt.  For symbol value,
index 0fa75d2..f69abf2 100644 (file)
@@ -1,7 +1,7 @@
 /* ELF executable support for BFD.
 
    Copyright 1993, 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001,
-   2002, 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010
+   2002, 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010, 2011
    Free Software Foundation, Inc.
 
    This file is part of BFD, the Binary File Descriptor library.
@@ -250,17 +250,18 @@ bfd_elf_allocate_object (bfd *abfd,
 
 
 bfd_boolean
-bfd_elf_make_generic_object (bfd *abfd)
+bfd_elf_make_object (bfd *abfd)
 {
+  const struct elf_backend_data *bed = get_elf_backend_data (abfd);
   return bfd_elf_allocate_object (abfd, sizeof (struct elf_obj_tdata),
-                                 GENERIC_ELF_DATA);
+                                 bed->target_id);
 }
 
 bfd_boolean
 bfd_elf_mkcorefile (bfd *abfd)
 {
   /* I think this can be done just like an object file.  */
-  return bfd_elf_make_generic_object (abfd);
+  return abfd->xvec->_bfd_set_format[(int) bfd_object] (abfd);
 }
 
 static char *
@@ -821,11 +822,7 @@ _bfd_elf_make_section_from_shdr (bfd *abfd,
   const struct elf_backend_data *bed;
 
   if (hdr->bfd_section != NULL)
-    {
-      BFD_ASSERT (strcmp (name,
-                         bfd_get_section_name (abfd, hdr->bfd_section)) == 0);
-      return TRUE;
-    }
+    return TRUE;
 
   newsect = bfd_make_section_anyway (abfd, name);
   if (newsect == NULL)
@@ -1008,6 +1005,77 @@ _bfd_elf_make_section_from_shdr (bfd *abfd,
        }
     }
 
+  /* Compress/decompress DWARF debug sections with names: .debug_* and
+     .zdebug_*, after the section flags is set.  */
+  if ((flags & SEC_DEBUGGING)
+      && ((name[1] == 'd' && name[6] == '_')
+         || (name[1] == 'z' && name[7] == '_')))
+    {
+      enum { nothing, compress, decompress } action = nothing;
+      char *new_name;
+
+      if (bfd_is_section_compressed (abfd, newsect))
+       {
+         /* Compressed section.  Check if we should decompress.  */
+         if ((abfd->flags & BFD_DECOMPRESS))
+           action = decompress;
+       }
+      else
+       {
+         /* Normal section.  Check if we should compress.  */
+         if ((abfd->flags & BFD_COMPRESS))
+           action = compress;
+       }
+
+      new_name = NULL;
+      switch (action)
+       {
+       case nothing:
+         break;
+       case compress:
+         if (!bfd_init_section_compress_status (abfd, newsect))
+           {
+             (*_bfd_error_handler)
+               (_("%B: unable to initialize commpress status for section %s"),
+                abfd, name);
+             return FALSE;
+           }
+         if (name[1] != 'z')
+           {
+             unsigned int len = strlen (name);
+
+             new_name = bfd_alloc (abfd, len + 2);
+             if (new_name == NULL)
+               return FALSE;
+             new_name[0] = '.';
+             new_name[1] = 'z';
+             memcpy (new_name + 2, name + 1, len);
+           }
+         break;
+       case decompress:
+         if (!bfd_init_section_decompress_status (abfd, newsect))
+           {
+             (*_bfd_error_handler)
+               (_("%B: unable to initialize decommpress status for section %s"),
+                abfd, name);
+             return FALSE;
+           }
+         if (name[1] == 'z')
+           {
+             unsigned int len = strlen (name);
+
+             new_name = bfd_alloc (abfd, len);
+             if (new_name == NULL)
+               return FALSE;
+             new_name[0] = '.';
+             memcpy (new_name + 1, name + 2, len - 1);
+           }
+         break;
+       }
+      if (new_name != NULL)
+       bfd_rename_section (abfd, newsect, new_name);
+    }
+
   return TRUE;
 }
 
@@ -1709,8 +1777,10 @@ bfd_section_from_shdr (bfd *abfd, unsigned int shindex)
       /* *These* do a lot of work -- but build no sections!  */
       {
        asection *target_sect;
-       Elf_Internal_Shdr *hdr2;
+       Elf_Internal_Shdr *hdr2, **p_hdr;
        unsigned int num_sec = elf_numsections (abfd);
+       struct bfd_elf_section_data *esdt;
+       bfd_size_type amt;
 
        if (hdr->sh_entsize
            != (bfd_size_type) (hdr->sh_type == SHT_REL
@@ -1789,20 +1859,19 @@ bfd_section_from_shdr (bfd *abfd, unsigned int shindex)
        if (target_sect == NULL)
          return FALSE;
 
-       if ((target_sect->flags & SEC_RELOC) == 0
-           || target_sect->reloc_count == 0)
-         hdr2 = &elf_section_data (target_sect)->rel_hdr;
+       esdt = elf_section_data (target_sect);
+       if (hdr->sh_type == SHT_RELA)
+         p_hdr = &esdt->rela.hdr;
        else
-         {
-           bfd_size_type amt;
-           BFD_ASSERT (elf_section_data (target_sect)->rel_hdr2 == NULL);
-           amt = sizeof (*hdr2);
-           hdr2 = (Elf_Internal_Shdr *) bfd_alloc (abfd, amt);
-           if (hdr2 == NULL)
-             return FALSE;
-           elf_section_data (target_sect)->rel_hdr2 = hdr2;
-         }
+         p_hdr = &esdt->rel.hdr;
+
+       BFD_ASSERT (*p_hdr == NULL);
+       amt = sizeof (*hdr2);
+       hdr2 = (Elf_Internal_Shdr *) bfd_alloc (abfd, amt);
+       if (hdr2 == NULL)
+         return FALSE;
        *hdr2 = *hdr;
+       *p_hdr = hdr2;
        elf_elfsections (abfd)[shindex] = hdr2;
        target_sect->reloc_count += NUM_SHDR_ENTRIES (hdr);
        target_sect->flags |= SEC_RELOC;
@@ -1811,7 +1880,10 @@ bfd_section_from_shdr (bfd *abfd, unsigned int shindex)
        /* In the section to which the relocations apply, mark whether
           its relocations are of the REL or RELA variety.  */
        if (hdr->sh_size != 0)
-         target_sect->use_rela_p = hdr->sh_type == SHT_RELA;
+         {
+           if (hdr->sh_type == SHT_RELA)
+             target_sect->use_rela_p = 1;
+         }
        abfd->flags |= HAS_RELOC;
        return TRUE;
       }
@@ -2010,6 +2082,7 @@ static const struct bfd_elf_special_section special_sections_f[] =
 static const struct bfd_elf_special_section special_sections_g[] =
 {
   { STRING_COMMA_LEN (".gnu.linkonce.b"), -2, SHT_NOBITS,      SHF_ALLOC + SHF_WRITE },
+  { STRING_COMMA_LEN (".gnu.lto_"),       -1, SHT_PROGBITS,    SHF_EXCLUDE },
   { STRING_COMMA_LEN (".got"),             0, SHT_PROGBITS,    SHF_ALLOC + SHF_WRITE },
   { STRING_COMMA_LEN (".gnu.version"),     0, SHT_GNU_versym,  0 },
   { STRING_COMMA_LEN (".gnu.version_d"),   0, SHT_GNU_verdef,  0 },
@@ -2231,12 +2304,19 @@ _bfd_elf_new_section_hook (bfd *abfd, asection *sec)
      anyway.  We will set ELF section type and flags for all linker
      created sections.  If user specifies BFD section flags, we will
      set ELF section type and flags based on BFD section flags in
-     elf_fake_sections.  */
-  if ((!sec->flags && abfd->direction != read_direction)
+     elf_fake_sections.  Special handling for .init_array/.fini_array
+     output sections since they may contain .ctors/.dtors input
+     sections.  We don't want _bfd_elf_init_private_section_data to
+     copy ELF section type from .ctors/.dtors input sections.  */
+  if (abfd->direction != read_direction
       || (sec->flags & SEC_LINKER_CREATED) != 0)
     {
       ssect = (*bed->get_sec_type_attr) (abfd, sec);
-      if (ssect != NULL)
+      if (ssect != NULL
+         && (!sec->flags
+             || (sec->flags & SEC_LINKER_CREATED) != 0
+             || ssect->type == SHT_INIT_ARRAY
+             || ssect->type == SHT_FINI_ARRAY))
        {
          elf_section_type (sec) = ssect->type;
          elf_section_flags (sec) = ssect->attr;
@@ -2409,20 +2489,43 @@ bfd_section_from_phdr (bfd *abfd, Elf_Internal_Phdr *hdr, int hdr_index)
     }
 }
 
-/* Initialize REL_HDR, the section-header for new section, containing
-   relocations against ASECT.  If USE_RELA_P is TRUE, we use RELA
-   relocations; otherwise, we use REL relocations.  */
+/* Return the REL_HDR for SEC, assuming there is only a single one, either
+   REL or RELA.  */
+
+Elf_Internal_Shdr *
+_bfd_elf_single_rel_hdr (asection *sec)
+{
+  if (elf_section_data (sec)->rel.hdr)
+    {
+      BFD_ASSERT (elf_section_data (sec)->rela.hdr == NULL);
+      return elf_section_data (sec)->rel.hdr;
+    }
+  else
+    return elf_section_data (sec)->rela.hdr;
+}
+
+/* Allocate and initialize a section-header for a new reloc section,
+   containing relocations against ASECT.  It is stored in RELDATA.  If
+   USE_RELA_P is TRUE, we use RELA relocations; otherwise, we use REL
+   relocations.  */
 
 bfd_boolean
 _bfd_elf_init_reloc_shdr (bfd *abfd,
-                         Elf_Internal_Shdr *rel_hdr,
+                         struct bfd_elf_section_reloc_data *reldata,
                          asection *asect,
                          bfd_boolean use_rela_p)
 {
+  Elf_Internal_Shdr *rel_hdr;
   char *name;
   const struct elf_backend_data *bed = get_elf_backend_data (abfd);
-  bfd_size_type amt = sizeof ".rela" + strlen (asect->name);
+  bfd_size_type amt;
 
+  amt = sizeof (Elf_Internal_Shdr);
+  BFD_ASSERT (reldata->hdr == NULL);
+  rel_hdr = bfd_zalloc (abfd, amt);
+  reldata->hdr = rel_hdr;
+
+  amt = sizeof ".rela" + strlen (asect->name);      
   name = (char *) bfd_alloc (abfd, amt);
   if (name == NULL)
     return FALSE;
@@ -2451,36 +2554,42 @@ int
 bfd_elf_get_default_section_type (flagword flags)
 {
   if ((flags & SEC_ALLOC) != 0
-      && ((flags & (SEC_LOAD | SEC_HAS_CONTENTS)) == 0
-         || (flags & SEC_NEVER_LOAD) != 0))
+      && (flags & (SEC_LOAD | SEC_HAS_CONTENTS)) == 0)
     return SHT_NOBITS;
   return SHT_PROGBITS;
 }
 
+struct fake_section_arg
+{
+  struct bfd_link_info *link_info;
+  bfd_boolean failed;
+};
+
 /* Set up an ELF internal section header for a section.  */
 
 static void
-elf_fake_sections (bfd *abfd, asection *asect, void *failedptrarg)
+elf_fake_sections (bfd *abfd, asection *asect, void *fsarg)
 {
+  struct fake_section_arg *arg = (struct fake_section_arg *)fsarg;
   const struct elf_backend_data *bed = get_elf_backend_data (abfd);
-  bfd_boolean *failedptr = (bfd_boolean *) failedptrarg;
+  struct bfd_elf_section_data *esd = elf_section_data (asect);
   Elf_Internal_Shdr *this_hdr;
   unsigned int sh_type;
 
-  if (*failedptr)
+  if (arg->failed)
     {
       /* We already failed; just get out of the bfd_map_over_sections
         loop.  */
       return;
     }
 
-  this_hdr = &elf_section_data (asect)->this_hdr;
+  this_hdr = &esd->this_hdr;
 
   this_hdr->sh_name = (unsigned int) _bfd_elf_strtab_add (elf_shstrtab (abfd),
                                                          asect->name, FALSE);
   if (this_hdr->sh_name == (unsigned int) -1)
     {
-      *failedptr = TRUE;
+      arg->failed = TRUE;
       return;
     }
 
@@ -2632,11 +2741,45 @@ elf_fake_sections (bfd *abfd, asection *asect, void *failedptrarg)
   if ((asect->flags & (SEC_GROUP | SEC_EXCLUDE)) == SEC_EXCLUDE)
     this_hdr->sh_flags |= SHF_EXCLUDE;
 
+  /* If the section has relocs, set up a section header for the
+     SHT_REL[A] section.  If two relocation sections are required for
+     this section, it is up to the processor-specific back-end to
+     create the other.  */
+  if ((asect->flags & SEC_RELOC) != 0)
+    {
+      /* When doing a relocatable link, create both REL and RELA sections if
+        needed.  */
+      if (arg->link_info
+         /* Do the normal setup if we wouldn't create any sections here.  */
+         && esd->rel.count + esd->rela.count > 0
+         && (arg->link_info->relocatable || arg->link_info->emitrelocations))
+       {
+         if (esd->rel.count && esd->rel.hdr == NULL
+             && !_bfd_elf_init_reloc_shdr (abfd, &esd->rel, asect, FALSE))
+           {
+             arg->failed = TRUE;
+             return;
+           }
+         if (esd->rela.count && esd->rela.hdr == NULL
+             && !_bfd_elf_init_reloc_shdr (abfd, &esd->rela, asect, TRUE))
+           {
+             arg->failed = TRUE;
+             return;
+           }
+       }
+      else if (!_bfd_elf_init_reloc_shdr (abfd,
+                                         (asect->use_rela_p
+                                          ? &esd->rela : &esd->rel),
+                                         asect,
+                                         asect->use_rela_p))
+         arg->failed = TRUE;
+    }
+
   /* Check for processor-specific section types.  */
   sh_type = this_hdr->sh_type;
   if (bed->elf_backend_fake_sections
       && !(*bed->elf_backend_fake_sections) (abfd, this_hdr, asect))
-    *failedptr = TRUE;
+    arg->failed = TRUE;
 
   if (sh_type == SHT_NOBITS && asect->size != 0)
     {
@@ -2644,17 +2787,6 @@ elf_fake_sections (bfd *abfd, asection *asect, void *failedptrarg)
         called for objcopy --only-keep-debug.  */
       this_hdr->sh_type = sh_type;
     }
-
-  /* If the section has relocs, set up a section header for the
-     SHT_REL[A] section.  If two relocation sections are required for
-     this section, it is up to the processor-specific back-end to
-     create the other.  */
-  if ((asect->flags & SEC_RELOC) != 0
-      && !_bfd_elf_init_reloc_shdr (abfd,
-                                   &elf_section_data (asect)->rel_hdr,
-                                   asect,
-                                   asect->use_rela_p))
-    *failedptr = TRUE;
 }
 
 /* Fill in the contents of a SHT_GROUP section.  Called from
@@ -2820,21 +2952,21 @@ assign_section_numbers (bfd *abfd, struct bfd_link_info *link_info)
       if (d->this_hdr.sh_type != SHT_GROUP)
        d->this_idx = section_number++;
       _bfd_elf_strtab_addref (elf_shstrtab (abfd), d->this_hdr.sh_name);
-      if ((sec->flags & SEC_RELOC) == 0)
-       d->rel_idx = 0;
-      else
+      if (d->rel.hdr)
        {
-         d->rel_idx = section_number++;
-         _bfd_elf_strtab_addref (elf_shstrtab (abfd), d->rel_hdr.sh_name);
+         d->rel.idx = section_number++;
+         _bfd_elf_strtab_addref (elf_shstrtab (abfd), d->rel.hdr->sh_name);
        }
+      else
+       d->rel.idx = 0;
 
-      if (d->rel_hdr2)
+      if (d->rela.hdr)
        {
-         d->rel_idx2 = section_number++;
-         _bfd_elf_strtab_addref (elf_shstrtab (abfd), d->rel_hdr2->sh_name);
+         d->rela.idx = section_number++;
+         _bfd_elf_strtab_addref (elf_shstrtab (abfd), d->rela.hdr->sh_name);
        }
       else
-       d->rel_idx2 = 0;
+       d->rela.idx = 0;
     }
 
   t->shstrtab_section = section_number++;
@@ -2906,25 +3038,25 @@ assign_section_numbers (bfd *abfd, struct bfd_link_info *link_info)
       d = elf_section_data (sec);
 
       i_shdrp[d->this_idx] = &d->this_hdr;
-      if (d->rel_idx != 0)
-       i_shdrp[d->rel_idx] = &d->rel_hdr;
-      if (d->rel_idx2 != 0)
-       i_shdrp[d->rel_idx2] = d->rel_hdr2;
+      if (d->rel.idx != 0)
+       i_shdrp[d->rel.idx] = d->rel.hdr;
+      if (d->rela.idx != 0)
+       i_shdrp[d->rela.idx] = d->rela.hdr;
 
       /* Fill in the sh_link and sh_info fields while we're at it.  */
 
       /* sh_link of a reloc section is the section index of the symbol
         table.  sh_info is the section index of the section to which
         the relocation entries apply.  */
-      if (d->rel_idx != 0)
+      if (d->rel.idx != 0)
        {
-         d->rel_hdr.sh_link = t->symtab_section;
-         d->rel_hdr.sh_info = d->this_idx;
+         d->rel.hdr->sh_link = t->symtab_section;
+         d->rel.hdr->sh_info = d->this_idx;
        }
-      if (d->rel_idx2 != 0)
+      if (d->rela.idx != 0)
        {
-         d->rel_hdr2->sh_link = t->symtab_section;
-         d->rel_hdr2->sh_info = d->this_idx;
+         d->rela.hdr->sh_link = t->symtab_section;
+         d->rela.hdr->sh_info = d->this_idx;
        }
 
       /* We need to set up sh_link for SHF_LINK_ORDER.  */
@@ -3278,6 +3410,7 @@ _bfd_elf_compute_section_file_positions (bfd *abfd,
                                         struct bfd_link_info *link_info)
 {
   const struct elf_backend_data *bed = get_elf_backend_data (abfd);
+  struct fake_section_arg fsargs;
   bfd_boolean failed;
   struct bfd_strtab_hash *strtab = NULL;
   Elf_Internal_Shdr *shstrtab_hdr;
@@ -3297,9 +3430,10 @@ _bfd_elf_compute_section_file_positions (bfd *abfd,
   if (bed->elf_backend_post_process_headers)
     (*bed->elf_backend_post_process_headers) (abfd, link_info);
 
-  failed = FALSE;
-  bfd_map_over_sections (abfd, elf_fake_sections, &failed);
-  if (failed)
+  fsargs.failed = FALSE;
+  fsargs.link_info = link_info;
+  bfd_map_over_sections (abfd, elf_fake_sections, &fsargs);
+  if (fsargs.failed)
     return FALSE;
 
   if (!assign_section_numbers (abfd, link_info))
@@ -3319,6 +3453,7 @@ _bfd_elf_compute_section_file_positions (bfd *abfd,
        return FALSE;
     }
 
+  failed = FALSE;
   if (link_info == NULL)
     {
       bfd_map_over_sections (abfd, bfd_elf_set_group_contents, &failed);
@@ -3624,6 +3759,7 @@ _bfd_elf_map_sections_to_segments (bfd *abfd, struct bfd_link_info *info)
       asection *first_tls = NULL;
       asection *dynsec, *eh_frame_hdr;
       bfd_size_type amt;
+      bfd_vma addr_mask, wrap_to = 0;
 
       /* Select the allocated sections, and sort them.  */
 
@@ -3632,6 +3768,12 @@ _bfd_elf_map_sections_to_segments (bfd *abfd, struct bfd_link_info *info)
       if (sections == NULL)
        goto error_return;
 
+      /* Calculate top address, avoiding undefined behaviour of shift
+        left operator when shift count is equal to size of type
+        being shifted.  */
+      addr_mask = ((bfd_vma) 1 << (bfd_arch_bits_per_address (abfd) - 1)) - 1;
+      addr_mask = (addr_mask << 1) + 1;
+
       i = 0;
       for (s = abfd->sections; s != NULL; s = s->next)
        {
@@ -3639,6 +3781,9 @@ _bfd_elf_map_sections_to_segments (bfd *abfd, struct bfd_link_info *info)
            {
              sections[i] = s;
              ++i;
+             /* A wrapping section potentially clashes with header.  */
+             if (((s->lma + s->size) & addr_mask) < (s->lma & addr_mask))
+               wrap_to = (s->lma + s->size) & addr_mask;
            }
        }
       BFD_ASSERT (i <= bfd_count_sections (abfd));
@@ -3708,8 +3853,10 @@ _bfd_elf_map_sections_to_segments (bfd *abfd, struct bfd_link_info *info)
          if (phdr_size == (bfd_size_type) -1)
            phdr_size = get_program_header_size (abfd, info);
          if ((abfd->flags & D_PAGED) == 0
-             || sections[0]->lma < phdr_size
-             || sections[0]->lma % maxpagesize < phdr_size % maxpagesize)
+             || (sections[0]->lma & addr_mask) < phdr_size
+             || ((sections[0]->lma & addr_mask) % maxpagesize
+                 < phdr_size % maxpagesize)
+             || (sections[0]->lma & addr_mask & -maxpagesize) < wrap_to)
            phdr_in_segment = FALSE;
        }
 
@@ -3736,6 +3883,13 @@ _bfd_elf_map_sections_to_segments (bfd *abfd, struct bfd_link_info *info)
                 segment.  */
              new_segment = TRUE;
            }
+         else if (hdr->lma < last_hdr->lma + last_size
+                  || last_hdr->lma + last_size < last_hdr->lma)
+           {
+             /* If this section has a load address that makes it overlap
+                the previous section, then we need a new segment.  */
+             new_segment = TRUE;
+           }
          /* In the next test we have to be careful when last_hdr->lma is close
             to the end of the address space.  If the aligned address wraps
             around to the start of the address space, then there are no more
@@ -3767,9 +3921,8 @@ _bfd_elf_map_sections_to_segments (bfd *abfd, struct bfd_link_info *info)
            }
          else if (! writable
                   && (hdr->flags & SEC_READONLY) == 0
-                  && (((last_hdr->lma + last_size - 1)
-                       & ~(maxpagesize - 1))
-                      != (hdr->lma & ~(maxpagesize - 1))))
+                  && (((last_hdr->lma + last_size - 1) & -maxpagesize)
+                      != (hdr->lma & -maxpagesize)))
            {
              /* We don't want to put a writable section in a read only
                 segment, unless they are on the same page in memory
@@ -3876,8 +4029,8 @@ _bfd_elf_map_sections_to_segments (bfd *abfd, struct bfd_link_info *info)
                    if (s2->next->alignment_power == 2
                        && (s2->next->flags & SEC_LOAD) != 0
                        && CONST_STRNEQ (s2->next->name, ".note")
-                       && align_power (s2->vma + s2->size, 2)
-                          == s2->next->vma)
+                       && align_power (s2->lma + s2->size, 2)
+                          == s2->next->lma)
                      count++;
                    else
                      break;
@@ -4127,10 +4280,12 @@ print_segment_map (const struct elf_segment_map *m)
                  (unsigned int) m->p_type);
       pt = buf;
     }
+  fflush (stdout);
   fprintf (stderr, "%s:", pt);
   for (j = 0; j < m->count; j++)
     fprintf (stderr, " %s", m->sections [j]->name);
   putc ('\n',stderr);
+  fflush (stderr);
 }
 
 static bfd_boolean
@@ -4179,8 +4334,18 @@ assign_file_positions_for_load_sections (bfd *abfd,
        header_pad = m->header_size;
     }
 
-  elf_elfheader (abfd)->e_phoff = bed->s->sizeof_ehdr;
-  elf_elfheader (abfd)->e_phentsize = bed->s->sizeof_phdr;
+  if (alloc)
+    {
+      elf_elfheader (abfd)->e_phoff = bed->s->sizeof_ehdr;
+      elf_elfheader (abfd)->e_phentsize = bed->s->sizeof_phdr;
+    }
+  else
+    {
+      /* PR binutils/12467.  */
+      elf_elfheader (abfd)->e_phoff = 0;
+      elf_elfheader (abfd)->e_phentsize = 0;
+    }
+  
   elf_elfheader (abfd)->e_phnum = alloc;
 
   if (elf_tdata (abfd)->program_header_size == (bfd_size_type) -1)
@@ -4330,7 +4495,7 @@ assign_file_positions_for_load_sections (bfd *abfd,
                break;
              }
 
-         off_adjust = vma_page_aligned_bias (m->sections[0]->vma, off, align);
+         off_adjust = vma_page_aligned_bias (p->p_vaddr, off, align);
          off += off_adjust;
          if (no_contents)
            {
@@ -4457,15 +4622,20 @@ assign_file_positions_for_load_sections (bfd *abfd,
                      && ((this_hdr->sh_flags & SHF_TLS) == 0
                          || p->p_type == PT_TLS))))
            {
-             bfd_vma adjust = sec->lma - (p->p_paddr + p->p_memsz);
-
-             if (sec->lma < p->p_paddr + p->p_memsz)
+             bfd_vma p_start = p->p_paddr;
+             bfd_vma p_end = p_start + p->p_memsz;
+             bfd_vma s_start = sec->lma;
+             bfd_vma adjust = s_start - p_end;
+
+             if (adjust != 0
+                 && (s_start < p_end
+                     || p_end < p_start))
                {
                  (*_bfd_error_handler)
-                   (_("%B: section %A lma 0x%lx overlaps previous sections"),
-                    abfd, sec, (unsigned long) sec->lma);
+                   (_("%B: section %A lma %#lx adjusted to %#lx"), abfd, sec,
+                    (unsigned long) s_start, (unsigned long) p_end);
                  adjust = 0;
-                 sec->lma = p->p_paddr + p->p_memsz;
+                 sec->lma = p_end;
                }
              p->p_memsz += adjust;
 
@@ -4578,8 +4748,7 @@ assign_file_positions_for_load_sections (bfd *abfd,
 
              sec = m->sections[i];
              this_hdr = &(elf_section_data(sec)->this_hdr);
-             if (this_hdr->sh_size != 0
-                 && !ELF_SECTION_IN_SEGMENT_1 (this_hdr, p, check_vma))
+             if (!ELF_SECTION_IN_SEGMENT_1 (this_hdr, p, check_vma, 0))
                {
                  (*_bfd_error_handler)
                    (_("%B: section `%A' can't be allocated in segment %d"),
@@ -4629,13 +4798,12 @@ assign_file_positions_for_non_load_sections (bfd *abfd,
        BFD_ASSERT (hdr->sh_offset == hdr->bfd_section->filepos);
       else if ((hdr->sh_flags & SHF_ALLOC) != 0)
        {
-         if (hdr->sh_size != 0)
-           ((*_bfd_error_handler)
-            (_("%B: warning: allocated section `%s' not in segment"),
-             abfd,
-             (hdr->bfd_section == NULL
-              ? "*unknown*"
-              : hdr->bfd_section->name)));
+         (*_bfd_error_handler)
+           (_("%B: warning: allocated section `%s' not in segment"),
+            abfd,
+            (hdr->bfd_section == NULL
+             ? "*unknown*"
+             : hdr->bfd_section->name));
          /* We don't need to page align empty sections.  */
          if ((abfd->flags & D_PAGED) != 0 && hdr->sh_size != 0)
            off += vma_page_aligned_bias (hdr->sh_addr, off,
@@ -5136,9 +5304,8 @@ _bfd_elf_symbol_from_bfd_symbol (bfd *abfd, asymbol **asym_ptr_ptr)
 #if DEBUG & 4
   {
     fprintf (stderr,
-            "elf_symbol_from_bfd_symbol 0x%.8lx, name = %s, sym num = %d, flags = 0x%.8lx%s\n",
-            (long) asym_ptr, asym_ptr->name, idx, flags,
-            elf_symbol_flags (flags));
+            "elf_symbol_from_bfd_symbol 0x%.8lx, name = %s, sym num = %d, flags = 0x%.8lx\n",
+            (long) asym_ptr, asym_ptr->name, idx, (long) flags);
     fflush (stderr);
   }
 #endif
@@ -5849,7 +6016,7 @@ copy_elf_program_header (bfd *ibfd, bfd *obfd)
       bfd_size_type amt;
       Elf_Internal_Shdr *this_hdr;
       asection *first_section = NULL;
-      asection *lowest_section = NULL;
+      asection *lowest_section;
 
       /* Compute how many sections are in this segment.  */
       for (section = ibfd->sections, section_count = 0;
@@ -5857,13 +6024,10 @@ copy_elf_program_header (bfd *ibfd, bfd *obfd)
           section = section->next)
        {
          this_hdr = &(elf_section_data(section)->this_hdr);
-         if (this_hdr->sh_size != 0
-             && ELF_SECTION_IN_SEGMENT (this_hdr, segment))
+         if (ELF_SECTION_IN_SEGMENT (this_hdr, segment))
            {
-             if (!first_section)
-               first_section = lowest_section = section;
-             if (section->lma < lowest_section->lma)
-               lowest_section = section;
+             if (first_section == NULL)
+               first_section = section;
              section_count++;
            }
        }
@@ -5917,17 +6081,7 @@ copy_elf_program_header (bfd *ibfd, bfd *obfd)
            phdr_included = TRUE;
        }
 
-      if (map->includes_filehdr && first_section)
-       /* We need to keep the space used by the headers fixed.  */
-       map->header_size = first_section->vma - segment->p_vaddr;
-      
-      if (!map->includes_phdrs
-         && !map->includes_filehdr
-         && map->p_paddr_valid)
-       /* There is some other padding before the first section.  */
-       map->p_vaddr_offset = ((lowest_section ? lowest_section->lma : 0)
-                              - segment->p_paddr);
-
+      lowest_section = first_section;
       if (section_count != 0)
        {
          unsigned int isec = 0;
@@ -5937,16 +6091,44 @@ copy_elf_program_header (bfd *ibfd, bfd *obfd)
               section = section->next)
            {
              this_hdr = &(elf_section_data(section)->this_hdr);
-             if (this_hdr->sh_size != 0
-                 && ELF_SECTION_IN_SEGMENT (this_hdr, segment))
+             if (ELF_SECTION_IN_SEGMENT (this_hdr, segment))
                {
                  map->sections[isec++] = section->output_section;
+                 if (section->lma < lowest_section->lma)
+                   lowest_section = section;
+                 if ((section->flags & SEC_ALLOC) != 0)
+                   {
+                     bfd_vma seg_off;
+
+                     /* Section lmas are set up from PT_LOAD header
+                        p_paddr in _bfd_elf_make_section_from_shdr.
+                        If this header has a p_paddr that disagrees
+                        with the section lma, flag the p_paddr as
+                        invalid.  */
+                     if ((section->flags & SEC_LOAD) != 0)
+                       seg_off = this_hdr->sh_offset - segment->p_offset;
+                     else
+                       seg_off = this_hdr->sh_addr - segment->p_vaddr;
+                     if (section->lma - segment->p_paddr != seg_off)
+                       map->p_paddr_valid = FALSE;
+                   }
                  if (isec == section_count)
                    break;
                }
            }
        }
 
+      if (map->includes_filehdr && lowest_section != NULL)
+       /* We need to keep the space used by the headers fixed.  */
+       map->header_size = lowest_section->vma - segment->p_vaddr;
+      
+      if (!map->includes_phdrs
+         && !map->includes_filehdr
+         && map->p_paddr_valid)
+       /* There is some other padding before the first section.  */
+       map->p_vaddr_offset = ((lowest_section ? lowest_section->lma : 0)
+                              - segment->p_paddr);
+
       map->count = section_count;
       *pointer_to_map = map;
       pointer_to_map = &map->next;
@@ -6015,8 +6197,7 @@ copy_private_bfd_data (bfd *ibfd, bfd *obfd)
 
              /* Check if this section is covered by the segment.  */
              this_hdr = &(elf_section_data(section)->this_hdr);
-             if (this_hdr->sh_size != 0
-                 && ELF_SECTION_IN_SEGMENT (this_hdr, segment))
+             if (ELF_SECTION_IN_SEGMENT (this_hdr, segment))
                {
                  /* FIXME: Check if its output section is changed or
                     removed.  What else do we need to check?  */
@@ -6075,7 +6256,7 @@ _bfd_elf_init_private_section_data (bfd *ibfd,
       && (osec->flags == isec->flags
          || (final_link
              && ((osec->flags ^ isec->flags)
-                 & ~ (SEC_LINK_ONCE | SEC_LINK_DUPLICATES)) == 0)))
+                 & ~(SEC_LINK_ONCE | SEC_LINK_DUPLICATES | SEC_RELOC)) == 0)))
     elf_section_type (osec) = elf_section_type (isec);
 
   /* FIXME: Is this correct for all OS/PROC specific flags?  */
@@ -6361,6 +6542,7 @@ swap_out_syms (bfd *abfd,
     sym.st_info = 0;
     sym.st_other = 0;
     sym.st_shndx = SHN_UNDEF;
+    sym.st_target_internal = 0;
     bed->s->swap_symbol_out (abfd, &sym, outbound_syms, outbound_shndx);
     outbound_syms += bed->s->sizeof_sym;
     if (outbound_shndx != NULL)
@@ -6560,9 +6742,16 @@ Unable to find equivalent output section for symbol '%s' from section '%s'"),
        }
 
       if (type_ptr != NULL)
-       sym.st_other = type_ptr->internal_elf_sym.st_other;
+       {
+         sym.st_other = type_ptr->internal_elf_sym.st_other;
+         sym.st_target_internal
+           = type_ptr->internal_elf_sym.st_target_internal;
+       }
       else
-       sym.st_other = 0;
+       {
+         sym.st_other = 0;
+         sym.st_target_internal = 0;
+       }
 
       bed->s->swap_symbol_out (abfd, &sym, outbound_syms, outbound_shndx);
       outbound_syms += bed->s->sizeof_sym;
@@ -7513,13 +7702,19 @@ _bfd_elf_rel_vtable_reloc_fn
 # include <sys/procfs.h>
 #endif
 
-/* FIXME: this is kinda wrong, but it's what gdb wants.  */
+/* Return a PID that identifies a "thread" for threaded cores, or the
+   PID of the main process for non-threaded cores.  */
 
 static int
 elfcore_make_pid (bfd *abfd)
 {
-  return ((elf_tdata (abfd)->core_lwpid << 16)
-         + (elf_tdata (abfd)->core_pid));
+  int pid;
+
+  pid = elf_tdata (abfd)->core_lwpid;
+  if (pid == 0)
+    pid = elf_tdata (abfd)->core_pid;
+
+  return pid;
 }
 
 /* If there isn't a section called NAME, make one, using
@@ -7609,7 +7804,8 @@ elfcore_grok_prstatus (bfd *abfd, Elf_Internal_Note *note)
         has already been set by another thread.  */
       if (elf_tdata (abfd)->core_signal == 0)
        elf_tdata (abfd)->core_signal = prstat.pr_cursig;
-      elf_tdata (abfd)->core_pid = prstat.pr_pid;
+      if (elf_tdata (abfd)->core_pid == 0)
+       elf_tdata (abfd)->core_pid = prstat.pr_pid;
 
       /* pr_who exists on:
         solaris 2.5+
@@ -7619,6 +7815,8 @@ elfcore_grok_prstatus (bfd *abfd, Elf_Internal_Note *note)
         */
 #if defined (HAVE_PRSTATUS_T_PR_WHO)
       elf_tdata (abfd)->core_lwpid = prstat.pr_who;
+#else
+      elf_tdata (abfd)->core_lwpid = prstat.pr_pid;
 #endif
     }
 #if defined (HAVE_PRSTATUS32_T)
@@ -7635,7 +7833,8 @@ elfcore_grok_prstatus (bfd *abfd, Elf_Internal_Note *note)
         has already been set by another thread.  */
       if (elf_tdata (abfd)->core_signal == 0)
        elf_tdata (abfd)->core_signal = prstat.pr_cursig;
-      elf_tdata (abfd)->core_pid = prstat.pr_pid;
+      if (elf_tdata (abfd)->core_pid == 0)
+       elf_tdata (abfd)->core_pid = prstat.pr_pid;
 
       /* pr_who exists on:
         solaris 2.5+
@@ -7645,6 +7844,8 @@ elfcore_grok_prstatus (bfd *abfd, Elf_Internal_Note *note)
         */
 #if defined (HAVE_PRSTATUS32_T_PR_WHO)
       elf_tdata (abfd)->core_lwpid = prstat.pr_who;
+#else
+      elf_tdata (abfd)->core_lwpid = prstat.pr_pid;
 #endif
     }
 #endif /* HAVE_PRSTATUS32_T */
index 7964c4f..693c8e8 100644 (file)
@@ -419,7 +419,7 @@ elf_i386_grok_prstatus (bfd *abfd, Elf_Internal_Note *note)
       elf_tdata (abfd)->core_signal = bfd_get_32 (abfd, note->descdata + 20);
 
       /* pr_pid */
-      elf_tdata (abfd)->core_pid = bfd_get_32 (abfd, note->descdata + 24);
+      elf_tdata (abfd)->core_lwpid = bfd_get_32 (abfd, note->descdata + 24);
 
       /* pr_reg */
       offset = 28;
@@ -437,7 +437,7 @@ elf_i386_grok_prstatus (bfd *abfd, Elf_Internal_Note *note)
          elf_tdata (abfd)->core_signal = bfd_get_16 (abfd, note->descdata + 12);
 
          /* pr_pid */
-         elf_tdata (abfd)->core_pid = bfd_get_32 (abfd, note->descdata + 24);
+         elf_tdata (abfd)->core_lwpid = bfd_get_32 (abfd, note->descdata + 24);
 
          /* pr_reg */
          offset = 72;
@@ -475,6 +475,8 @@ elf_i386_grok_psinfo (bfd *abfd, Elf_Internal_Note *note)
          return FALSE;
 
        case 124:               /* Linux/i386 elf_prpsinfo.  */
+         elf_tdata (abfd)->core_pid
+           = bfd_get_32 (abfd, note->descdata + 12);
          elf_tdata (abfd)->core_program
            = _bfd_elfcore_strndup (abfd, note->descdata + 28, 16);
          elf_tdata (abfd)->core_command
@@ -789,8 +791,6 @@ elf_i386_get_local_sym_hash (struct elf_i386_link_hash_table *htab,
       ret->elf.indx = sec->id;
       ret->elf.dynstr_index = ELF32_R_SYM (rel->r_info);
       ret->elf.dynindx = -1;
-      ret->elf.plt.offset = (bfd_vma) -1;
-      ret->elf.got.offset = (bfd_vma) -1;
       *slot = ret;
     }
   return &ret->elf;
@@ -1162,6 +1162,12 @@ elf_i386_tls_transition (struct bfd_link_info *info, bfd *abfd,
   unsigned int to_type = from_type;
   bfd_boolean check = TRUE;
 
+  /* Skip TLS transition for functions.  */
+  if (h != NULL
+      && (h->type == STT_FUNC
+         || h->type == STT_GNU_IFUNC))
+    return TRUE;
+
   switch (from_type)
     {
     case R_386_TLS_GD:
@@ -1330,8 +1336,7 @@ elf_i386_check_relocs (bfd *abfd,
          /* Check relocation against local STT_GNU_IFUNC symbol.  */
          if (ELF32_ST_TYPE (isym->st_info) == STT_GNU_IFUNC)
            {
-             h = elf_i386_get_local_sym_hash (htab, abfd, rel,
-                                                  TRUE);
+             h = elf_i386_get_local_sym_hash (htab, abfd, rel, TRUE);
              if (h == NULL)
                return FALSE;
 
@@ -1802,16 +1807,36 @@ elf_i386_gc_sweep_hook (bfd *abfd,
       r_symndx = ELF32_R_SYM (rel->r_info);
       if (r_symndx >= symtab_hdr->sh_info)
        {
-         struct elf_i386_link_hash_entry *eh;
-         struct elf_dyn_relocs **pp;
-         struct elf_dyn_relocs *p;
-
          h = sym_hashes[r_symndx - symtab_hdr->sh_info];
          while (h->root.type == bfd_link_hash_indirect
                 || h->root.type == bfd_link_hash_warning)
            h = (struct elf_link_hash_entry *) h->root.u.i.link;
-         eh = (struct elf_i386_link_hash_entry *) h;
+       }
+      else
+       {
+         /* A local symbol.  */
+         Elf_Internal_Sym *isym;
+
+         isym = bfd_sym_from_r_symndx (&htab->sym_cache,
+                                       abfd, r_symndx);
+
+         /* Check relocation against local STT_GNU_IFUNC symbol.  */
+         if (isym != NULL
+             && ELF32_ST_TYPE (isym->st_info) == STT_GNU_IFUNC)
+           {
+             h = elf_i386_get_local_sym_hash (htab, abfd, rel, FALSE);
+             if (h == NULL)
+               abort ();
+           }
+       }
+
+      if (h)
+       {
+         struct elf_i386_link_hash_entry *eh;
+         struct elf_dyn_relocs **pp;
+         struct elf_dyn_relocs *p;
 
+         eh = (struct elf_i386_link_hash_entry *) h;
          for (pp = &eh->dyn_relocs; (p = *pp) != NULL; pp = &p->next)
            if (p->sec == sec)
              {
@@ -1846,6 +1871,11 @@ elf_i386_gc_sweep_hook (bfd *abfd,
            {
              if (h->got.refcount > 0)
                h->got.refcount -= 1;
+             if (h->type == STT_GNU_IFUNC)
+               {
+                 if (h->plt.refcount > 0)
+                   h->plt.refcount -= 1;
+               }
            }
          else if (local_got_refcounts != NULL)
            {
@@ -1856,7 +1886,8 @@ elf_i386_gc_sweep_hook (bfd *abfd,
 
        case R_386_32:
        case R_386_PC32:
-         if (info->shared)
+         if (info->shared
+             && (h == NULL || h->type != STT_GNU_IFUNC))
            break;
          /* Fall through */
 
@@ -1868,6 +1899,16 @@ elf_i386_gc_sweep_hook (bfd *abfd,
            }
          break;
 
+       case R_386_GOTOFF:
+         if (h != NULL && h->type == STT_GNU_IFUNC)
+           {
+             if (h->got.refcount > 0)
+               h->got.refcount -= 1;
+             if (h->plt.refcount > 0)
+               h->plt.refcount -= 1;
+           }
+         break;
+
        default:
          break;
        }
@@ -2520,6 +2561,30 @@ elf_i386_size_dynamic_sections (bfd *output_bfd ATTRIBUTE_UNUSED,
   if (htab->elf.srelplt)
     htab->sgotplt_jump_table_size = htab->next_tls_desc_index * 4;
 
+  if (htab->elf.sgotplt)
+    {
+      struct elf_link_hash_entry *got;
+      got = elf_link_hash_lookup (elf_hash_table (info),
+                                 "_GLOBAL_OFFSET_TABLE_",
+                                 FALSE, FALSE, FALSE);
+
+      /* Don't allocate .got.plt section if there are no GOT nor PLT
+         entries and there is no refeence to _GLOBAL_OFFSET_TABLE_.  */
+      if ((got == NULL
+          || !got->ref_regular_nonweak)
+         && (htab->elf.sgotplt->size
+             == get_elf_backend_data (output_bfd)->got_header_size)
+         && (htab->elf.splt == NULL
+             || htab->elf.splt->size == 0)
+         && (htab->elf.sgot == NULL
+             || htab->elf.sgot->size == 0)
+         && (htab->elf.iplt == NULL
+             || htab->elf.iplt->size == 0)
+         && (htab->elf.igotplt == NULL
+             || htab->elf.igotplt->size == 0))
+       htab->elf.sgotplt->size = 0;
+    }
+
   /* We now have determined the sizes of the various dynamic sections.
      Allocate memory for them.  */
   relocs = FALSE;
@@ -2767,11 +2832,16 @@ static bfd_vma
 elf_i386_tpoff (struct bfd_link_info *info, bfd_vma address)
 {
   struct elf_link_hash_table *htab = elf_hash_table (info);
+  const struct elf_backend_data *bed = get_elf_backend_data (info->output_bfd);
+  bfd_vma static_tls_size;
 
   /* If tls_sec is NULL, we should have signalled an error already.  */
   if (htab->tls_sec == NULL)
     return 0;
-  return htab->tls_size + htab->tls_sec->vma - address;
+
+  /* Consider special static TLS alignment requirements.  */
+  static_tls_size = BFD_ALIGN (htab->tls_size, bed->static_tls_alignment);
+  return static_tls_size + htab->tls_sec->vma - address;
 }
 
 /* Relocate an i386 ELF section.  */
@@ -2934,8 +3004,8 @@ elf_i386_relocate_section (bfd *output_bfd,
                   && ELF32_ST_TYPE (sym->st_info) == STT_GNU_IFUNC)
            {
              /* Relocate against local STT_GNU_IFUNC symbol.  */
-             h = elf_i386_get_local_sym_hash (htab, input_bfd,
-                                                  rel, FALSE);
+             h = elf_i386_get_local_sym_hash (htab, input_bfd, rel,
+                                              FALSE);
              if (h == NULL)
                abort ();
 
@@ -3058,7 +3128,7 @@ elf_i386_relocate_section (bfd *output_bfd,
                     internal symbol, we have updated addend.  */
                  continue;
                }
-
+             /* FALLTHROUGH */
            case R_386_PC32:
            case R_386_PLT32:
              goto do_relocation;
@@ -4561,6 +4631,13 @@ elf_i386_finish_dynamic_sections (bfd *output_bfd,
 
   if (htab->elf.sgotplt)
     {
+      if (bfd_is_abs_section (htab->elf.sgotplt->output_section))
+       {
+         (*_bfd_error_handler)
+           (_("discarded output section: `%A'"), htab->elf.sgotplt);
+         return FALSE;
+       }
+
       /* Fill in the first three entries in the global offset table.  */
       if (htab->elf.sgotplt->size > 0)
        {
@@ -4631,6 +4708,7 @@ elf_i386_add_symbol_hook (bfd * abfd,
 #define TARGET_LITTLE_SYM              bfd_elf32_i386_vec
 #define TARGET_LITTLE_NAME             "elf32-i386"
 #define ELF_ARCH                       bfd_arch_i386
+#define ELF_TARGET_ID                  I386_ELF_DATA
 #define ELF_MACHINE_CODE               EM_386
 #define ELF_MAXPAGESIZE                        0x1000
 
@@ -4726,6 +4804,11 @@ elf_i386_fbsd_post_process_headers (bfd *abfd, struct bfd_link_info *info)
 #undef elf32_bed
 #define        elf32_bed                       elf32_i386_sol2_bed
 
+/* The 32-bit static TLS arena size is rounded to the nearest 8-byte
+   boundary.  */
+#undef elf_backend_static_tls_alignment
+#define elf_backend_static_tls_alignment 8
+
 /* The Solaris 2 ABI requires a plt symbol on all platforms.
 
    Cf. Linker and Libraries Guide, Ch. 2, Link-Editor, Generating the Output
@@ -4779,6 +4862,7 @@ elf_i386_vxworks_link_hash_table_create (bfd *abfd)
 #undef elf_backend_final_write_processing
 #define elf_backend_final_write_processing \
   elf_vxworks_final_write_processing
+#undef elf_backend_static_tls_alignment
 
 /* On VxWorks, we emit relocations against _PROCEDURE_LINKAGE_TABLE_, so
    define it.  */
index 21524fa..927b3ed 100644 (file)
@@ -1,4 +1,4 @@
-/* X86-64 specific support for 64-bit ELF
+/* X86-64 specific support for ELF
    Copyright 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, 2009,
    2010  Free Software Foundation, Inc.
    Contributed by Jan Hubicka <jh@suse.cz>.
 /* In case we're on a 32-bit machine, construct a 64-bit "-1" value.  */
 #define MINUS_ONE (~ (bfd_vma) 0)
 
+/* Since both 32-bit and 64-bit x86-64 encode relocation type in the
+   identical manner, we use ELF32_R_TYPE instead of ELF64_R_TYPE to get
+   relocation type.  We also use ELF_ST_TYPE instead of ELF64_ST_TYPE
+   since they are the same.  */
+
+#define ABI_64_P(abfd) \
+  (get_elf_backend_data (abfd)->s->elfclass == ELFCLASS64)
+
 /* The relocation "howto" table.  Order of fields:
    type, rightshift, size, bitsize, pc_relative, bitpos, complain_on_overflow,
    special_function, name, partial_inplace, src_mask, dst_mask, pcrel_offset.  */
@@ -222,7 +230,7 @@ static const struct elf_reloc_map x86_64_reloc_map[] =
 };
 
 static reloc_howto_type *
-elf64_x86_64_rtype_to_howto (bfd *abfd, unsigned r_type)
+elf_x86_64_rtype_to_howto (bfd *abfd, unsigned r_type)
 {
   unsigned i;
 
@@ -245,8 +253,8 @@ elf64_x86_64_rtype_to_howto (bfd *abfd, unsigned r_type)
 
 /* Given a BFD reloc type, return a HOWTO structure.  */
 static reloc_howto_type *
-elf64_x86_64_reloc_type_lookup (bfd *abfd,
-                               bfd_reloc_code_real_type code)
+elf_x86_64_reloc_type_lookup (bfd *abfd,
+                             bfd_reloc_code_real_type code)
 {
   unsigned int i;
 
@@ -254,15 +262,15 @@ elf64_x86_64_reloc_type_lookup (bfd *abfd,
        i++)
     {
       if (x86_64_reloc_map[i].bfd_reloc_val == code)
-       return elf64_x86_64_rtype_to_howto (abfd,
-                                           x86_64_reloc_map[i].elf_reloc_val);
+       return elf_x86_64_rtype_to_howto (abfd,
+                                         x86_64_reloc_map[i].elf_reloc_val);
     }
   return 0;
 }
 
 static reloc_howto_type *
-elf64_x86_64_reloc_name_lookup (bfd *abfd ATTRIBUTE_UNUSED,
-                               const char *r_name)
+elf_x86_64_reloc_name_lookup (bfd *abfd ATTRIBUTE_UNUSED,
+                             const char *r_name)
 {
   unsigned int i;
 
@@ -280,19 +288,19 @@ elf64_x86_64_reloc_name_lookup (bfd *abfd ATTRIBUTE_UNUSED,
 /* Given an x86_64 ELF reloc type, fill in an arelent structure.  */
 
 static void
-elf64_x86_64_info_to_howto (bfd *abfd ATTRIBUTE_UNUSED, arelent *cache_ptr,
-                           Elf_Internal_Rela *dst)
+elf_x86_64_info_to_howto (bfd *abfd ATTRIBUTE_UNUSED, arelent *cache_ptr,
+                         Elf_Internal_Rela *dst)
 {
   unsigned r_type;
 
-  r_type = ELF64_R_TYPE (dst->r_info);
-  cache_ptr->howto = elf64_x86_64_rtype_to_howto (abfd, r_type);
+  r_type = ELF32_R_TYPE (dst->r_info);
+  cache_ptr->howto = elf_x86_64_rtype_to_howto (abfd, r_type);
   BFD_ASSERT (r_type == cache_ptr->howto->type);
 }
 \f
 /* Support for core dump NOTE sections.  */
 static bfd_boolean
-elf64_x86_64_grok_prstatus (bfd *abfd, Elf_Internal_Note *note)
+elf_x86_64_grok_prstatus (bfd *abfd, Elf_Internal_Note *note)
 {
   int offset;
   size_t size;
@@ -308,7 +316,7 @@ elf64_x86_64_grok_prstatus (bfd *abfd, Elf_Internal_Note *note)
          = bfd_get_16 (abfd, note->descdata + 12);
 
        /* pr_pid */
-       elf_tdata (abfd)->core_pid
+       elf_tdata (abfd)->core_lwpid
          = bfd_get_32 (abfd, note->descdata + 32);
 
        /* pr_reg */
@@ -324,7 +332,7 @@ elf64_x86_64_grok_prstatus (bfd *abfd, Elf_Internal_Note *note)
 }
 
 static bfd_boolean
-elf64_x86_64_grok_psinfo (bfd *abfd, Elf_Internal_Note *note)
+elf_x86_64_grok_psinfo (bfd *abfd, Elf_Internal_Note *note)
 {
   switch (note->descsz)
     {
@@ -332,6 +340,8 @@ elf64_x86_64_grok_psinfo (bfd *abfd, Elf_Internal_Note *note)
        return FALSE;
 
       case 136:                /* sizeof(struct elf_prpsinfo) on Linux/x86_64 */
+       elf_tdata (abfd)->core_pid
+         = bfd_get_32 (abfd, note->descdata + 24);
        elf_tdata (abfd)->core_program
         = _bfd_elfcore_strndup (abfd, note->descdata + 40, 16);
        elf_tdata (abfd)->core_command
@@ -358,7 +368,8 @@ elf64_x86_64_grok_psinfo (bfd *abfd, Elf_Internal_Note *note)
 /* The name of the dynamic interpreter.         This is put in the .interp
    section.  */
 
-#define ELF_DYNAMIC_INTERPRETER "/lib/ld64.so.1"
+#define ELF64_DYNAMIC_INTERPRETER "/lib/ld64.so.1"
+#define ELF32_DYNAMIC_INTERPRETER "/lib/ld32.so.1"
 
 /* If ELIMINATE_COPY_RELOCS is non-zero, the linker will try to avoid
    copying dynamic variables from a shared lib into an app's dynbss
@@ -377,7 +388,7 @@ elf64_x86_64_grok_psinfo (bfd *abfd, Elf_Internal_Note *note)
 /* The first entry in a procedure linkage table looks like this.  See the
    SVR4 ABI i386 supplement and the x86-64 ABI to see how this works.  */
 
-static const bfd_byte elf64_x86_64_plt0_entry[PLT_ENTRY_SIZE] =
+static const bfd_byte elf_x86_64_plt0_entry[PLT_ENTRY_SIZE] =
 {
   0xff, 0x35, 8, 0, 0, 0,      /* pushq GOT+8(%rip)  */
   0xff, 0x25, 16, 0, 0, 0,     /* jmpq *GOT+16(%rip) */
@@ -386,7 +397,7 @@ static const bfd_byte elf64_x86_64_plt0_entry[PLT_ENTRY_SIZE] =
 
 /* Subsequent entries in a procedure linkage table look like this.  */
 
-static const bfd_byte elf64_x86_64_plt_entry[PLT_ENTRY_SIZE] =
+static const bfd_byte elf_x86_64_plt_entry[PLT_ENTRY_SIZE] =
 {
   0xff, 0x25,  /* jmpq *name@GOTPC(%rip) */
   0, 0, 0, 0,  /* replaced with offset to this symbol in .got.  */
@@ -398,7 +409,7 @@ static const bfd_byte elf64_x86_64_plt_entry[PLT_ENTRY_SIZE] =
 
 /* x86-64 ELF linker hash entry.  */
 
-struct elf64_x86_64_link_hash_entry
+struct elf_x86_64_link_hash_entry
 {
   struct elf_link_hash_entry elf;
 
@@ -425,10 +436,10 @@ struct elf64_x86_64_link_hash_entry
   bfd_vma tlsdesc_got;
 };
 
-#define elf64_x86_64_hash_entry(ent) \
-  ((struct elf64_x86_64_link_hash_entry *)(ent))
+#define elf_x86_64_hash_entry(ent) \
+  ((struct elf_x86_64_link_hash_entry *)(ent))
 
-struct elf64_x86_64_obj_tdata
+struct elf_x86_64_obj_tdata
 {
   struct elf_obj_tdata root;
 
@@ -439,14 +450,14 @@ struct elf64_x86_64_obj_tdata
   bfd_vma *local_tlsdesc_gotent;
 };
 
-#define elf64_x86_64_tdata(abfd) \
-  ((struct elf64_x86_64_obj_tdata *) (abfd)->tdata.any)
+#define elf_x86_64_tdata(abfd) \
+  ((struct elf_x86_64_obj_tdata *) (abfd)->tdata.any)
 
-#define elf64_x86_64_local_got_tls_type(abfd) \
-  (elf64_x86_64_tdata (abfd)->local_got_tls_type)
+#define elf_x86_64_local_got_tls_type(abfd) \
+  (elf_x86_64_tdata (abfd)->local_got_tls_type)
 
-#define elf64_x86_64_local_tlsdesc_gotent(abfd) \
-  (elf64_x86_64_tdata (abfd)->local_tlsdesc_gotent)
+#define elf_x86_64_local_tlsdesc_gotent(abfd) \
+  (elf_x86_64_tdata (abfd)->local_tlsdesc_gotent)
 
 #define is_x86_64_elf(bfd)                             \
   (bfd_get_flavour (bfd) == bfd_target_elf_flavour     \
@@ -454,15 +465,15 @@ struct elf64_x86_64_obj_tdata
    && elf_object_id (bfd) == X86_64_ELF_DATA)
 
 static bfd_boolean
-elf64_x86_64_mkobject (bfd *abfd)
+elf_x86_64_mkobject (bfd *abfd)
 {
-  return bfd_elf_allocate_object (abfd, sizeof (struct elf64_x86_64_obj_tdata),
+  return bfd_elf_allocate_object (abfd, sizeof (struct elf_x86_64_obj_tdata),
                                  X86_64_ELF_DATA);
 }
 
 /* x86-64 ELF linker hash table.  */
 
-struct elf64_x86_64_link_hash_table
+struct elf_x86_64_link_hash_table
 {
   struct elf_link_hash_table elf;
 
@@ -482,6 +493,12 @@ struct elf64_x86_64_link_hash_table
   /* Small local sym cache.  */
   struct sym_cache sym_cache;
 
+  bfd_vma (*r_info) (bfd_vma, bfd_vma);
+  bfd_vma (*r_sym) (bfd_vma);
+  unsigned int pointer_r_type;
+  const char *dynamic_interpreter;
+  int dynamic_interpreter_size;
+
   /* _TLS_MODULE_BASE_ symbol.  */
   struct bfd_link_hash_entry *tls_module_base;
 
@@ -501,19 +518,19 @@ struct elf64_x86_64_link_hash_table
 
 /* Get the x86-64 ELF linker hash table from a link_info structure.  */
 
-#define elf64_x86_64_hash_table(p) \
+#define elf_x86_64_hash_table(p) \
   (elf_hash_table_id ((struct elf_link_hash_table *) ((p)->hash)) \
-  == X86_64_ELF_DATA ? ((struct elf64_x86_64_link_hash_table *) ((p)->hash)) : NULL)
+  == X86_64_ELF_DATA ? ((struct elf_x86_64_link_hash_table *) ((p)->hash)) : NULL)
 
-#define elf64_x86_64_compute_jump_table_size(htab) \
+#define elf_x86_64_compute_jump_table_size(htab) \
   ((htab)->elf.srelplt->reloc_count * GOT_ENTRY_SIZE)
 
 /* Create an entry in an x86-64 ELF linker hash table. */
 
 static struct bfd_hash_entry *
-elf64_x86_64_link_hash_newfunc (struct bfd_hash_entry *entry,
-                               struct bfd_hash_table *table,
-                               const char *string)
+elf_x86_64_link_hash_newfunc (struct bfd_hash_entry *entry,
+                             struct bfd_hash_table *table,
+                             const char *string)
 {
   /* Allocate the structure if it has not already been allocated by a
      subclass.  */
@@ -521,7 +538,7 @@ elf64_x86_64_link_hash_newfunc (struct bfd_hash_entry *entry,
     {
       entry = (struct bfd_hash_entry *)
           bfd_hash_allocate (table,
-                             sizeof (struct elf64_x86_64_link_hash_entry));
+                             sizeof (struct elf_x86_64_link_hash_entry));
       if (entry == NULL)
        return entry;
     }
@@ -530,9 +547,9 @@ elf64_x86_64_link_hash_newfunc (struct bfd_hash_entry *entry,
   entry = _bfd_elf_link_hash_newfunc (entry, table, string);
   if (entry != NULL)
     {
-      struct elf64_x86_64_link_hash_entry *eh;
+      struct elf_x86_64_link_hash_entry *eh;
 
-      eh = (struct elf64_x86_64_link_hash_entry *) entry;
+      eh = (struct elf_x86_64_link_hash_entry *) entry;
       eh->dyn_relocs = NULL;
       eh->tls_type = GOT_UNKNOWN;
       eh->tlsdesc_got = (bfd_vma) -1;
@@ -547,7 +564,7 @@ elf64_x86_64_link_hash_newfunc (struct bfd_hash_entry *entry,
   hash since they aren't used by global symbols in this backend.  */
 
 static hashval_t
-elf64_x86_64_local_htab_hash (const void *ptr)
+elf_x86_64_local_htab_hash (const void *ptr)
 {
   struct elf_link_hash_entry *h
     = (struct elf_link_hash_entry *) ptr;
@@ -557,7 +574,7 @@ elf64_x86_64_local_htab_hash (const void *ptr)
 /* Compare local hash entries.  */
 
 static int
-elf64_x86_64_local_htab_eq (const void *ptr1, const void *ptr2)
+elf_x86_64_local_htab_eq (const void *ptr1, const void *ptr2)
 {
   struct elf_link_hash_entry *h1
      = (struct elf_link_hash_entry *) ptr1;
@@ -570,18 +587,18 @@ elf64_x86_64_local_htab_eq (const void *ptr1, const void *ptr2)
 /* Find and/or create a hash entry for local symbol.  */
 
 static struct elf_link_hash_entry *
-elf64_x86_64_get_local_sym_hash (struct elf64_x86_64_link_hash_table *htab,
-                                bfd *abfd, const Elf_Internal_Rela *rel,
-                                bfd_boolean create)
+elf_x86_64_get_local_sym_hash (struct elf_x86_64_link_hash_table *htab,
+                              bfd *abfd, const Elf_Internal_Rela *rel,
+                              bfd_boolean create)
 {
-  struct elf64_x86_64_link_hash_entry e, *ret;
+  struct elf_x86_64_link_hash_entry e, *ret;
   asection *sec = abfd->sections;
   hashval_t h = ELF_LOCAL_SYMBOL_HASH (sec->id,
-                                      ELF64_R_SYM (rel->r_info));
+                                      htab->r_sym (rel->r_info));
   void **slot;
 
   e.elf.indx = sec->id;
-  e.elf.dynstr_index = ELF64_R_SYM (rel->r_info);
+  e.elf.dynstr_index = htab->r_sym (rel->r_info);
   slot = htab_find_slot_with_hash (htab->loc_hash_table, &e, h,
                                   create ? INSERT : NO_INSERT);
 
@@ -590,21 +607,19 @@ elf64_x86_64_get_local_sym_hash (struct elf64_x86_64_link_hash_table *htab,
 
   if (*slot)
     {
-      ret = (struct elf64_x86_64_link_hash_entry *) *slot;
+      ret = (struct elf_x86_64_link_hash_entry *) *slot;
       return &ret->elf;
     }
 
-  ret = (struct elf64_x86_64_link_hash_entry *)
+  ret = (struct elf_x86_64_link_hash_entry *)
        objalloc_alloc ((struct objalloc *) htab->loc_hash_memory,
-                       sizeof (struct elf64_x86_64_link_hash_entry));
+                       sizeof (struct elf_x86_64_link_hash_entry));
   if (ret)
     {
       memset (ret, 0, sizeof (*ret));
       ret->elf.indx = sec->id;
-      ret->elf.dynstr_index = ELF64_R_SYM (rel->r_info);
+      ret->elf.dynstr_index = htab->r_sym (rel->r_info);
       ret->elf.dynindx = -1;
-      ret->elf.plt.offset = (bfd_vma) -1;
-      ret->elf.got.offset = (bfd_vma) -1;
       *slot = ret;
     }
   return &ret->elf;
@@ -613,18 +628,18 @@ elf64_x86_64_get_local_sym_hash (struct elf64_x86_64_link_hash_table *htab,
 /* Create an X86-64 ELF linker hash table.  */
 
 static struct bfd_link_hash_table *
-elf64_x86_64_link_hash_table_create (bfd *abfd)
+elf_x86_64_link_hash_table_create (bfd *abfd)
 {
-  struct elf64_x86_64_link_hash_table *ret;
-  bfd_size_type amt = sizeof (struct elf64_x86_64_link_hash_table);
+  struct elf_x86_64_link_hash_table *ret;
+  bfd_size_type amt = sizeof (struct elf_x86_64_link_hash_table);
 
-  ret = (struct elf64_x86_64_link_hash_table *) bfd_malloc (amt);
+  ret = (struct elf_x86_64_link_hash_table *) bfd_malloc (amt);
   if (ret == NULL)
     return NULL;
 
   if (!_bfd_elf_link_hash_table_init (&ret->elf, abfd,
-                                     elf64_x86_64_link_hash_newfunc,
-                                     sizeof (struct elf64_x86_64_link_hash_entry),
+                                     elf_x86_64_link_hash_newfunc,
+                                     sizeof (struct elf_x86_64_link_hash_entry),
                                      X86_64_ELF_DATA))
     {
       free (ret);
@@ -640,9 +655,26 @@ elf64_x86_64_link_hash_table_create (bfd *abfd)
   ret->sgotplt_jump_table_size = 0;
   ret->tls_module_base = NULL;
 
+  if (ABI_64_P (abfd))
+    {
+      ret->r_info = elf64_r_info;
+      ret->r_sym = elf64_r_sym;
+      ret->pointer_r_type = R_X86_64_64;
+      ret->dynamic_interpreter = ELF64_DYNAMIC_INTERPRETER;
+      ret->dynamic_interpreter_size = sizeof ELF64_DYNAMIC_INTERPRETER;
+    }
+  else
+    {
+      ret->r_info = elf32_r_info;
+      ret->r_sym = elf32_r_sym;
+      ret->pointer_r_type = R_X86_64_32;
+      ret->dynamic_interpreter = ELF32_DYNAMIC_INTERPRETER;
+      ret->dynamic_interpreter_size = sizeof ELF32_DYNAMIC_INTERPRETER;
+    }
+
   ret->loc_hash_table = htab_try_create (1024,
-                                        elf64_x86_64_local_htab_hash,
-                                        elf64_x86_64_local_htab_eq,
+                                        elf_x86_64_local_htab_hash,
+                                        elf_x86_64_local_htab_eq,
                                         NULL);
   ret->loc_hash_memory = objalloc_create ();
   if (!ret->loc_hash_table || !ret->loc_hash_memory)
@@ -657,10 +689,10 @@ elf64_x86_64_link_hash_table_create (bfd *abfd)
 /* Destroy an X86-64 ELF linker hash table.  */
 
 static void
-elf64_x86_64_link_hash_table_free (struct bfd_link_hash_table *hash)
+elf_x86_64_link_hash_table_free (struct bfd_link_hash_table *hash)
 {
-  struct elf64_x86_64_link_hash_table *htab
-    = (struct elf64_x86_64_link_hash_table *) hash;
+  struct elf_x86_64_link_hash_table *htab
+    = (struct elf_x86_64_link_hash_table *) hash;
 
   if (htab->loc_hash_table)
     htab_delete (htab->loc_hash_table);
@@ -674,14 +706,15 @@ elf64_x86_64_link_hash_table_free (struct bfd_link_hash_table *hash)
    hash table.  */
 
 static bfd_boolean
-elf64_x86_64_create_dynamic_sections (bfd *dynobj, struct bfd_link_info *info)
+elf_x86_64_create_dynamic_sections (bfd *dynobj,
+                                   struct bfd_link_info *info)
 {
-  struct elf64_x86_64_link_hash_table *htab;
+  struct elf_x86_64_link_hash_table *htab;
 
   if (!_bfd_elf_create_dynamic_sections (dynobj, info))
     return FALSE;
 
-  htab = elf64_x86_64_hash_table (info);
+  htab = elf_x86_64_hash_table (info);
   if (htab == NULL)
     return FALSE;
 
@@ -699,14 +732,14 @@ elf64_x86_64_create_dynamic_sections (bfd *dynobj, struct bfd_link_info *info)
 /* Copy the extra info we tack onto an elf_link_hash_entry.  */
 
 static void
-elf64_x86_64_copy_indirect_symbol (struct bfd_link_info *info,
-                                  struct elf_link_hash_entry *dir,
-                                  struct elf_link_hash_entry *ind)
+elf_x86_64_copy_indirect_symbol (struct bfd_link_info *info,
+                                struct elf_link_hash_entry *dir,
+                                struct elf_link_hash_entry *ind)
 {
-  struct elf64_x86_64_link_hash_entry *edir, *eind;
+  struct elf_x86_64_link_hash_entry *edir, *eind;
 
-  edir = (struct elf64_x86_64_link_hash_entry *) dir;
-  eind = (struct elf64_x86_64_link_hash_entry *) ind;
+  edir = (struct elf_x86_64_link_hash_entry *) dir;
+  eind = (struct elf_x86_64_link_hash_entry *) ind;
 
   if (eind->dyn_relocs != NULL)
     {
@@ -789,18 +822,21 @@ x86_64_opcode32;
    from R_TYPE.  */
 
 static bfd_boolean
-elf64_x86_64_check_tls_transition (bfd *abfd, asection *sec,
-                                  bfd_byte *contents,
-                                  Elf_Internal_Shdr *symtab_hdr,
-                                  struct elf_link_hash_entry **sym_hashes,
-                                  unsigned int r_type,
-                                  const Elf_Internal_Rela *rel,
-                                  const Elf_Internal_Rela *relend)
+elf_x86_64_check_tls_transition (bfd *abfd,
+                                struct bfd_link_info *info,
+                                asection *sec,
+                                bfd_byte *contents,
+                                Elf_Internal_Shdr *symtab_hdr,
+                                struct elf_link_hash_entry **sym_hashes,
+                                unsigned int r_type,
+                                const Elf_Internal_Rela *rel,
+                                const Elf_Internal_Rela *relend)
 {
   unsigned int val;
   unsigned long r_symndx;
   struct elf_link_hash_entry *h;
   bfd_vma offset;
+  struct elf_x86_64_link_hash_table *htab;
 
   /* Get the section contents.  */
   if (contents == NULL)
@@ -818,6 +854,7 @@ elf64_x86_64_check_tls_transition (bfd *abfd, asection *sec,
        }
     }
 
+  htab = elf_x86_64_hash_table (info);
   offset = rel->r_offset;
   switch (r_type)
     {
@@ -828,18 +865,34 @@ elf64_x86_64_check_tls_transition (bfd *abfd, asection *sec,
 
       if (r_type == R_X86_64_TLSGD)
        {
-         /* Check transition from GD access model.  Only
+         /* Check transition from GD access model.  For 64bit, only
                .byte 0x66; leaq foo@tlsgd(%rip), %rdi
                .word 0x6666; rex64; call __tls_get_addr
+            can transit to different access model.  For 32bit, only
+               leaq foo@tlsgd(%rip), %rdi
+               .word 0x6666; rex64; call __tls_get_addr
             can transit to different access model.  */
 
-         static x86_64_opcode32 leaq = { { 0x66, 0x48, 0x8d, 0x3d } },
-                                call = { { 0x66, 0x66, 0x48, 0xe8 } };
-         if (offset < 4
-             || (offset + 12) > sec->size
-             || bfd_get_32 (abfd, contents + offset - 4) != leaq.i
+         static x86_64_opcode32 call = { { 0x66, 0x66, 0x48, 0xe8 } };
+         if ((offset + 12) > sec->size
              || bfd_get_32 (abfd, contents + offset + 4) != call.i)
            return FALSE;
+
+         if (ABI_64_P (abfd))
+           {
+             static x86_64_opcode32 leaq = { { 0x66, 0x48, 0x8d, 0x3d } };
+             if (offset < 4
+                 || bfd_get_32 (abfd, contents + offset - 4) != leaq.i)
+               return FALSE;
+           }
+         else
+           {
+             static x86_64_opcode16 lea = { { 0x8d, 0x3d } };
+             if (offset < 3
+                 || bfd_get_8 (abfd, contents + offset - 3) != 0x48
+                 || bfd_get_16 (abfd, contents + offset - 2) != lea.i)
+               return FALSE;
+           }
        }
       else
        {
@@ -860,7 +913,7 @@ elf64_x86_64_check_tls_transition (bfd *abfd, asection *sec,
            return FALSE;
        }
 
-      r_symndx = ELF64_R_SYM (rel[1].r_info);
+      r_symndx = htab->r_sym (rel[1].r_info);
       if (r_symndx < symtab_hdr->sh_info)
        return FALSE;
 
@@ -869,23 +922,36 @@ elf64_x86_64_check_tls_transition (bfd *abfd, asection *sec,
         may be versioned.  */ 
       return (h != NULL
              && h->root.root.string != NULL
-             && (ELF64_R_TYPE (rel[1].r_info) == R_X86_64_PC32
-                 || ELF64_R_TYPE (rel[1].r_info) == R_X86_64_PLT32)
+             && (ELF32_R_TYPE (rel[1].r_info) == R_X86_64_PC32
+                 || ELF32_R_TYPE (rel[1].r_info) == R_X86_64_PLT32)
              && (strncmp (h->root.root.string,
                           "__tls_get_addr", 14) == 0));
 
     case R_X86_64_GOTTPOFF:
       /* Check transition from IE access model:
-               movq foo@gottpoff(%rip), %reg
-               addq foo@gottpoff(%rip), %reg
+               mov foo@gottpoff(%rip), %reg
+               add foo@gottpoff(%rip), %reg
        */
 
-      if (offset < 3 || (offset + 4) > sec->size)
-       return FALSE;
-
-      val = bfd_get_8 (abfd, contents + offset - 3);
-      if (val != 0x48 && val != 0x4c)
-       return FALSE;
+      /* Check REX prefix first.  */
+      if (offset >= 3 && (offset + 4) <= sec->size)
+       {
+         val = bfd_get_8 (abfd, contents + offset - 3);
+         if (val != 0x48 && val != 0x4c)
+           {
+             /* X32 may have 0x44 REX prefix or no REX prefix.  */
+             if (ABI_64_P (abfd))
+               return FALSE;
+           }
+       }
+      else
+       {
+         /* X32 may not have any REX prefix.  */
+         if (ABI_64_P (abfd))
+           return FALSE;
+         if (offset < 2 || (offset + 3) > sec->size)
+           return FALSE;
+       }
 
       val = bfd_get_8 (abfd, contents + offset - 2);
       if (val != 0x8b && val != 0x03)
@@ -937,20 +1003,26 @@ elf64_x86_64_check_tls_transition (bfd *abfd, asection *sec,
    will be performed.  Update R_TYPE if there is a transition.  */
 
 static bfd_boolean
-elf64_x86_64_tls_transition (struct bfd_link_info *info, bfd *abfd,
-                            asection *sec, bfd_byte *contents,
-                            Elf_Internal_Shdr *symtab_hdr,
-                            struct elf_link_hash_entry **sym_hashes,
-                            unsigned int *r_type, int tls_type,
-                            const Elf_Internal_Rela *rel,
-                            const Elf_Internal_Rela *relend,
-                            struct elf_link_hash_entry *h,
-                            unsigned long r_symndx)
+elf_x86_64_tls_transition (struct bfd_link_info *info, bfd *abfd,
+                          asection *sec, bfd_byte *contents,
+                          Elf_Internal_Shdr *symtab_hdr,
+                          struct elf_link_hash_entry **sym_hashes,
+                          unsigned int *r_type, int tls_type,
+                          const Elf_Internal_Rela *rel,
+                          const Elf_Internal_Rela *relend,
+                          struct elf_link_hash_entry *h,
+                          unsigned long r_symndx)
 {
   unsigned int from_type = *r_type;
   unsigned int to_type = from_type;
   bfd_boolean check = TRUE;
 
+  /* Skip TLS transition for functions.  */
+  if (h != NULL
+      && (h->type == STT_FUNC
+         || h->type == STT_GNU_IFUNC))
+    return TRUE;
+
   switch (from_type)
     {
     case R_X86_64_TLSGD:
@@ -965,7 +1037,7 @@ elf64_x86_64_tls_transition (struct bfd_link_info *info, bfd *abfd,
            to_type = R_X86_64_GOTTPOFF;
        }
 
-      /* When we are called from elf64_x86_64_relocate_section,
+      /* When we are called from elf_x86_64_relocate_section,
         CONTENTS isn't NULL and there may be additional transitions
         based on TLS_TYPE.  */
       if (contents != NULL)
@@ -987,7 +1059,7 @@ elf64_x86_64_tls_transition (struct bfd_link_info *info, bfd *abfd,
            }
 
          /* We checked the transition before when we were called from
-            elf64_x86_64_check_relocs.  We only want to check the new
+            elf_x86_64_check_relocs.  We only want to check the new
             transition which hasn't been checked before.  */
          check = new_to_type != to_type && from_type == to_type;
          to_type = new_to_type;
@@ -1010,23 +1082,23 @@ elf64_x86_64_tls_transition (struct bfd_link_info *info, bfd *abfd,
 
   /* Check if the transition can be performed.  */
   if (check
-      && ! elf64_x86_64_check_tls_transition (abfd, sec, contents,
-                                             symtab_hdr, sym_hashes,
-                                             from_type, rel, relend))
+      && ! elf_x86_64_check_tls_transition (abfd, info, sec, contents,
+                                           symtab_hdr, sym_hashes,
+                                           from_type, rel, relend))
     {
       reloc_howto_type *from, *to;
       const char *name;
 
-      from = elf64_x86_64_rtype_to_howto (abfd, from_type);
-      to = elf64_x86_64_rtype_to_howto (abfd, to_type);
+      from = elf_x86_64_rtype_to_howto (abfd, from_type);
+      to = elf_x86_64_rtype_to_howto (abfd, to_type);
 
       if (h)
        name = h->root.root.string;
       else
        {
-         struct elf64_x86_64_link_hash_table *htab;
+         struct elf_x86_64_link_hash_table *htab;
 
-         htab = elf64_x86_64_hash_table (info);
+         htab = elf_x86_64_hash_table (info);
          if (htab == NULL)
            name = "*unknown*";
          else
@@ -1057,11 +1129,11 @@ elf64_x86_64_tls_transition (struct bfd_link_info *info, bfd *abfd,
    linkage table, and dynamic reloc sections.  */
 
 static bfd_boolean
-elf64_x86_64_check_relocs (bfd *abfd, struct bfd_link_info *info,
-                          asection *sec,
-                          const Elf_Internal_Rela *relocs)
+elf_x86_64_check_relocs (bfd *abfd, struct bfd_link_info *info,
+                        asection *sec,
+                        const Elf_Internal_Rela *relocs)
 {
-  struct elf64_x86_64_link_hash_table *htab;
+  struct elf_x86_64_link_hash_table *htab;
   Elf_Internal_Shdr *symtab_hdr;
   struct elf_link_hash_entry **sym_hashes;
   const Elf_Internal_Rela *rel;
@@ -1073,7 +1145,7 @@ elf64_x86_64_check_relocs (bfd *abfd, struct bfd_link_info *info,
 
   BFD_ASSERT (is_x86_64_elf (abfd));
 
-  htab = elf64_x86_64_hash_table (info);
+  htab = elf_x86_64_hash_table (info);
   if (htab == NULL)
     return FALSE;
 
@@ -1091,8 +1163,8 @@ elf64_x86_64_check_relocs (bfd *abfd, struct bfd_link_info *info,
       Elf_Internal_Sym *isym;
       const char *name;
 
-      r_symndx = ELF64_R_SYM (rel->r_info);
-      r_type = ELF64_R_TYPE (rel->r_info);
+      r_symndx = htab->r_sym (rel->r_info);
+      r_type = ELF32_R_TYPE (rel->r_info);
 
       if (r_symndx >= NUM_SHDR_ENTRIES (symtab_hdr))
        {
@@ -1110,10 +1182,10 @@ elf64_x86_64_check_relocs (bfd *abfd, struct bfd_link_info *info,
            return FALSE;
 
          /* Check relocation against local STT_GNU_IFUNC symbol.  */
-         if (ELF64_ST_TYPE (isym->st_info) == STT_GNU_IFUNC)
+         if (ELF_ST_TYPE (isym->st_info) == STT_GNU_IFUNC)
            {
-             h = elf64_x86_64_get_local_sym_hash (htab, abfd, rel,
-                                                  TRUE);
+             h = elf_x86_64_get_local_sym_hash (htab, abfd, rel,
+                                                TRUE);
              if (h == NULL)
                return FALSE;
 
@@ -1136,6 +1208,39 @@ elf64_x86_64_check_relocs (bfd *abfd, struct bfd_link_info *info,
            h = (struct elf_link_hash_entry *) h->root.u.i.link;
        }
 
+      /* Check invalid x32 relocations.  */
+      if (!ABI_64_P (abfd))
+       switch (r_type)
+         {
+         default:
+           break;
+
+         case R_X86_64_64:
+         case R_X86_64_DTPOFF64:
+         case R_X86_64_TPOFF64:
+         case R_X86_64_PC64:
+         case R_X86_64_GOTOFF64:
+         case R_X86_64_GOT64:
+         case R_X86_64_GOTPCREL64:
+         case R_X86_64_GOTPC64:
+         case R_X86_64_GOTPLT64:
+         case R_X86_64_PLTOFF64:
+             {
+               if (h)
+                 name = h->root.root.string;
+               else
+                 name = bfd_elf_sym_name (abfd, symtab_hdr, isym,
+                                          NULL);
+               (*_bfd_error_handler)
+                 (_("%B: relocation %s against symbol `%s' isn't "
+                    "supported in x32 mode"), abfd,
+                  x86_64_elf_howto_table[r_type].name, name);
+               bfd_set_error (bfd_error_bad_value);
+               return FALSE;
+             }
+           break;
+         }
+
       if (h != NULL)
        {
          /* Create the ifunc sections for static executables.  If we
@@ -1192,6 +1297,9 @@ elf64_x86_64_check_relocs (bfd *abfd, struct bfd_link_info *info,
                  bfd_set_error (bfd_error_bad_value);
                  return FALSE;
 
+               case R_X86_64_32:
+                 if (ABI_64_P (abfd))
+                   goto not_pointer;
                case R_X86_64_64:
                  h->non_got_ref = 1;
                  h->pointer_equality_needed = 1;
@@ -1202,16 +1310,16 @@ elf64_x86_64_check_relocs (bfd *abfd, struct bfd_link_info *info,
                         make room for this reloc.  */
                      sreloc = _bfd_elf_create_ifunc_dyn_reloc
                        (abfd, info, sec, sreloc,
-                        &((struct elf64_x86_64_link_hash_entry *) h)->dyn_relocs);
+                        &((struct elf_x86_64_link_hash_entry *) h)->dyn_relocs);
                      if (sreloc == NULL)
                        return FALSE;
                    }
                  break;
 
                case R_X86_64_32S:
-               case R_X86_64_32:
                case R_X86_64_PC32:
                case R_X86_64_PC64:
+not_pointer:
                  h->non_got_ref = 1;
                  if (r_type != R_X86_64_PC32
                      && r_type != R_X86_64_PC64)
@@ -1235,10 +1343,10 @@ elf64_x86_64_check_relocs (bfd *abfd, struct bfd_link_info *info,
            }
        }
 
-      if (! elf64_x86_64_tls_transition (info, abfd, sec, NULL,
-                                        symtab_hdr, sym_hashes,
-                                        &r_type, GOT_UNKNOWN,
-                                        rel, rel_end, h, r_symndx))
+      if (! elf_x86_64_tls_transition (info, abfd, sec, NULL,
+                                      symtab_hdr, sym_hashes,
+                                      &r_type, GOT_UNKNOWN,
+                                      rel, rel_end, h, r_symndx))
        return FALSE;
 
       switch (r_type)
@@ -1248,7 +1356,7 @@ elf64_x86_64_check_relocs (bfd *abfd, struct bfd_link_info *info,
          goto create_got;
 
        case R_X86_64_TPOFF32:
-         if (!info->executable)
+         if (!info->executable && ABI_64_P (abfd))
            {
              if (h)
                name = h->root.root.string;
@@ -1302,7 +1410,7 @@ elf64_x86_64_check_relocs (bfd *abfd, struct bfd_link_info *info,
                    h->plt.refcount += 1;
                  }
                h->got.refcount += 1;
-               old_tls_type = elf64_x86_64_hash_entry (h)->tls_type;
+               old_tls_type = elf_x86_64_hash_entry (h)->tls_type;
              }
            else
              {
@@ -1322,14 +1430,14 @@ elf64_x86_64_check_relocs (bfd *abfd, struct bfd_link_info *info,
                    if (local_got_refcounts == NULL)
                      return FALSE;
                    elf_local_got_refcounts (abfd) = local_got_refcounts;
-                   elf64_x86_64_local_tlsdesc_gotent (abfd)
+                   elf_x86_64_local_tlsdesc_gotent (abfd)
                      = (bfd_vma *) (local_got_refcounts + symtab_hdr->sh_info);
-                   elf64_x86_64_local_got_tls_type (abfd)
+                   elf_x86_64_local_got_tls_type (abfd)
                      = (char *) (local_got_refcounts + 2 * symtab_hdr->sh_info);
                  }
                local_got_refcounts[r_symndx] += 1;
                old_tls_type
-                 = elf64_x86_64_local_got_tls_type (abfd) [r_symndx];
+                 = elf_x86_64_local_got_tls_type (abfd) [r_symndx];
              }
 
            /* If a TLS symbol is accessed using IE at least once,
@@ -1360,9 +1468,9 @@ elf64_x86_64_check_relocs (bfd *abfd, struct bfd_link_info *info,
            if (old_tls_type != tls_type)
              {
                if (h != NULL)
-                 elf64_x86_64_hash_entry (h)->tls_type = tls_type;
+                 elf_x86_64_hash_entry (h)->tls_type = tls_type;
                else
-                 elf64_x86_64_local_got_tls_type (abfd) [r_symndx] = tls_type;
+                 elf_x86_64_local_got_tls_type (abfd) [r_symndx] = tls_type;
              }
          }
          /* Fall through */
@@ -1408,9 +1516,11 @@ elf64_x86_64_check_relocs (bfd *abfd, struct bfd_link_info *info,
            }
          goto create_got;
 
+       case R_X86_64_32:
+         if (!ABI_64_P (abfd))
+           goto pointer;
        case R_X86_64_8:
        case R_X86_64_16:
-       case R_X86_64_32:
        case R_X86_64_32S:
          /* Let's help debug shared library creation.  These relocs
             cannot be used in shared libs.  Don't error out for
@@ -1437,6 +1547,7 @@ elf64_x86_64_check_relocs (bfd *abfd, struct bfd_link_info *info,
        case R_X86_64_PC32:
        case R_X86_64_PC64:
        case R_X86_64_64:
+pointer:
          if (h != NULL && info->executable)
            {
              /* If this reloc is in a read-only section, we might
@@ -1501,7 +1612,8 @@ elf64_x86_64_check_relocs (bfd *abfd, struct bfd_link_info *info,
                    htab->elf.dynobj = abfd;
 
                  sreloc = _bfd_elf_make_dynamic_reloc_section
-                   (sec, htab->elf.dynobj, 3, abfd, /*rela?*/ TRUE);
+                   (sec, htab->elf.dynobj, ABI_64_P (abfd) ? 3 : 2,
+                    abfd, /*rela?*/ TRUE);
 
                  if (sreloc == NULL)
                    return FALSE;
@@ -1511,7 +1623,7 @@ elf64_x86_64_check_relocs (bfd *abfd, struct bfd_link_info *info,
                 relocations we need for this symbol.  */
              if (h != NULL)
                {
-                 head = &((struct elf64_x86_64_link_hash_entry *) h)->dyn_relocs;
+                 head = &((struct elf_x86_64_link_hash_entry *) h)->dyn_relocs;
                }
              else
                {
@@ -1586,14 +1698,14 @@ elf64_x86_64_check_relocs (bfd *abfd, struct bfd_link_info *info,
    relocation. */
 
 static asection *
-elf64_x86_64_gc_mark_hook (asection *sec,
-                          struct bfd_link_info *info,
-                          Elf_Internal_Rela *rel,
-                          struct elf_link_hash_entry *h,
-                          Elf_Internal_Sym *sym)
+elf_x86_64_gc_mark_hook (asection *sec,
+                        struct bfd_link_info *info,
+                        Elf_Internal_Rela *rel,
+                        struct elf_link_hash_entry *h,
+                        Elf_Internal_Sym *sym)
 {
   if (h != NULL)
-    switch (ELF64_R_TYPE (rel->r_info))
+    switch (ELF32_R_TYPE (rel->r_info))
       {
       case R_X86_64_GNU_VTINHERIT:
       case R_X86_64_GNU_VTENTRY:
@@ -1606,11 +1718,11 @@ elf64_x86_64_gc_mark_hook (asection *sec,
 /* Update the got entry reference counts for the section being removed.         */
 
 static bfd_boolean
-elf64_x86_64_gc_sweep_hook (bfd *abfd, struct bfd_link_info *info,
-                           asection *sec,
-                           const Elf_Internal_Rela *relocs)
+elf_x86_64_gc_sweep_hook (bfd *abfd, struct bfd_link_info *info,
+                         asection *sec,
+                         const Elf_Internal_Rela *relocs)
 {
-  struct elf64_x86_64_link_hash_table *htab;
+  struct elf_x86_64_link_hash_table *htab;
   Elf_Internal_Shdr *symtab_hdr;
   struct elf_link_hash_entry **sym_hashes;
   bfd_signed_vma *local_got_refcounts;
@@ -1619,7 +1731,7 @@ elf64_x86_64_gc_sweep_hook (bfd *abfd, struct bfd_link_info *info,
   if (info->relocatable)
     return TRUE;
 
-  htab = elf64_x86_64_hash_table (info);
+  htab = elf_x86_64_hash_table (info);
   if (htab == NULL)
     return FALSE;
 
@@ -1629,6 +1741,7 @@ elf64_x86_64_gc_sweep_hook (bfd *abfd, struct bfd_link_info *info,
   sym_hashes = elf_sym_hashes (abfd);
   local_got_refcounts = elf_local_got_refcounts (abfd);
 
+  htab = elf_x86_64_hash_table (info);
   relend = relocs + sec->reloc_count;
   for (rel = relocs; rel < relend; rel++)
     {
@@ -1636,18 +1749,39 @@ elf64_x86_64_gc_sweep_hook (bfd *abfd, struct bfd_link_info *info,
       unsigned int r_type;
       struct elf_link_hash_entry *h = NULL;
 
-      r_symndx = ELF64_R_SYM (rel->r_info);
+      r_symndx = htab->r_sym (rel->r_info);
       if (r_symndx >= symtab_hdr->sh_info)
        {
-         struct elf64_x86_64_link_hash_entry *eh;
-         struct elf_dyn_relocs **pp;
-         struct elf_dyn_relocs *p;
-
          h = sym_hashes[r_symndx - symtab_hdr->sh_info];
          while (h->root.type == bfd_link_hash_indirect
                 || h->root.type == bfd_link_hash_warning)
            h = (struct elf_link_hash_entry *) h->root.u.i.link;
-         eh = (struct elf64_x86_64_link_hash_entry *) h;
+       }
+      else
+       {
+         /* A local symbol.  */
+         Elf_Internal_Sym *isym;
+
+         isym = bfd_sym_from_r_symndx (&htab->sym_cache,
+                                       abfd, r_symndx);
+
+         /* Check relocation against local STT_GNU_IFUNC symbol.  */
+         if (isym != NULL
+             && ELF_ST_TYPE (isym->st_info) == STT_GNU_IFUNC)
+           {
+             h = elf_x86_64_get_local_sym_hash (htab, abfd, rel, FALSE);
+             if (h == NULL)
+               abort ();
+           }
+       }
+
+      if (h)
+       {
+         struct elf_x86_64_link_hash_entry *eh;
+         struct elf_dyn_relocs **pp;
+         struct elf_dyn_relocs *p;
+
+         eh = (struct elf_x86_64_link_hash_entry *) h;
 
          for (pp = &eh->dyn_relocs; (p = *pp) != NULL; pp = &p->next)
            if (p->sec == sec)
@@ -1658,11 +1792,11 @@ elf64_x86_64_gc_sweep_hook (bfd *abfd, struct bfd_link_info *info,
              }
        }
 
-      r_type = ELF64_R_TYPE (rel->r_info);
-      if (! elf64_x86_64_tls_transition (info, abfd, sec, NULL,
-                                        symtab_hdr, sym_hashes,
-                                        &r_type, GOT_UNKNOWN,
-                                        rel, relend, h, r_symndx))
+      r_type = ELF32_R_TYPE (rel->r_info);
+      if (! elf_x86_64_tls_transition (info, abfd, sec, NULL,
+                                      symtab_hdr, sym_hashes,
+                                      &r_type, GOT_UNKNOWN,
+                                      rel, relend, h, r_symndx))
        return FALSE;
 
       switch (r_type)
@@ -1687,6 +1821,11 @@ elf64_x86_64_gc_sweep_hook (bfd *abfd, struct bfd_link_info *info,
                h->plt.refcount -= 1;
              if (h->got.refcount > 0)
                h->got.refcount -= 1;
+             if (h->type == STT_GNU_IFUNC)
+               {
+                 if (h->plt.refcount > 0)
+                   h->plt.refcount -= 1;
+               }
            }
          else if (local_got_refcounts != NULL)
            {
@@ -1704,7 +1843,8 @@ elf64_x86_64_gc_sweep_hook (bfd *abfd, struct bfd_link_info *info,
        case R_X86_64_PC16:
        case R_X86_64_PC32:
        case R_X86_64_PC64:
-         if (info->shared)
+         if (info->shared
+             && (h == NULL || h->type != STT_GNU_IFUNC))
            break;
          /* Fall thru */
 
@@ -1732,10 +1872,10 @@ elf64_x86_64_gc_sweep_hook (bfd *abfd, struct bfd_link_info *info,
    understand. */
 
 static bfd_boolean
-elf64_x86_64_adjust_dynamic_symbol (struct bfd_link_info *info,
-                                   struct elf_link_hash_entry *h)
+elf_x86_64_adjust_dynamic_symbol (struct bfd_link_info *info,
+                                 struct elf_link_hash_entry *h)
 {
-  struct elf64_x86_64_link_hash_table *htab;
+  struct elf_x86_64_link_hash_table *htab;
   asection *s;
 
   /* STT_GNU_IFUNC symbol must go through PLT. */
@@ -1817,10 +1957,10 @@ elf64_x86_64_adjust_dynamic_symbol (struct bfd_link_info *info,
 
   if (ELIMINATE_COPY_RELOCS)
     {
-      struct elf64_x86_64_link_hash_entry * eh;
+      struct elf_x86_64_link_hash_entry * eh;
       struct elf_dyn_relocs *p;
 
-      eh = (struct elf64_x86_64_link_hash_entry *) h;
+      eh = (struct elf_x86_64_link_hash_entry *) h;
       for (p = eh->dyn_relocs; p != NULL; p = p->next)
        {
          s = p->sec->output_section;
@@ -1854,7 +1994,7 @@ elf64_x86_64_adjust_dynamic_symbol (struct bfd_link_info *info,
      both the dynamic object and the regular object will refer to the
      same memory location for the variable.  */
 
-  htab = elf64_x86_64_hash_table (info);
+  htab = elf_x86_64_hash_table (info);
   if (htab == NULL)
     return FALSE;
 
@@ -1863,7 +2003,9 @@ elf64_x86_64_adjust_dynamic_symbol (struct bfd_link_info *info,
      runtime process image.  */
   if ((h->root.u.def.section->flags & SEC_ALLOC) != 0)
     {
-      htab->srelbss->size += sizeof (Elf64_External_Rela);
+      const struct elf_backend_data *bed;
+      bed = get_elf_backend_data (info->output_bfd);
+      htab->srelbss->size += bed->s->sizeof_rela;
       h->needs_copy = 1;
     }
 
@@ -1876,24 +2018,26 @@ elf64_x86_64_adjust_dynamic_symbol (struct bfd_link_info *info,
    dynamic relocs.  */
 
 static bfd_boolean
-elf64_x86_64_allocate_dynrelocs (struct elf_link_hash_entry *h, void * inf)
+elf_x86_64_allocate_dynrelocs (struct elf_link_hash_entry *h, void * inf)
 {
   struct bfd_link_info *info;
-  struct elf64_x86_64_link_hash_table *htab;
-  struct elf64_x86_64_link_hash_entry *eh;
+  struct elf_x86_64_link_hash_table *htab;
+  struct elf_x86_64_link_hash_entry *eh;
   struct elf_dyn_relocs *p;
+  const struct elf_backend_data *bed;
 
   if (h->root.type == bfd_link_hash_indirect)
     return TRUE;
 
   if (h->root.type == bfd_link_hash_warning)
     h = (struct elf_link_hash_entry *) h->root.u.i.link;
-  eh = (struct elf64_x86_64_link_hash_entry *) h;
+  eh = (struct elf_x86_64_link_hash_entry *) h;
 
   info = (struct bfd_link_info *) inf;
-  htab = elf64_x86_64_hash_table (info);
+  htab = elf_x86_64_hash_table (info);
   if (htab == NULL)
     return FALSE;
+  bed = get_elf_backend_data (info->output_bfd);
 
   /* Since STT_GNU_IFUNC symbol must go through PLT, we handle it
      here if it is defined and referenced in a non-shared object.  */
@@ -1947,7 +2091,7 @@ elf64_x86_64_allocate_dynrelocs (struct elf_link_hash_entry *h, void * inf)
          htab->elf.sgotplt->size += GOT_ENTRY_SIZE;
 
          /* We also need to make an entry in the .rela.plt section.  */
-         htab->elf.srelplt->size += sizeof (Elf64_External_Rela);
+         htab->elf.srelplt->size += bed->s->sizeof_rela;
          htab->elf.srelplt->reloc_count++;
        }
       else
@@ -1969,7 +2113,7 @@ elf64_x86_64_allocate_dynrelocs (struct elf_link_hash_entry *h, void * inf)
   if (h->got.refcount > 0
       && info->executable
       && h->dynindx == -1
-      && elf64_x86_64_hash_entry (h)->tls_type == GOT_TLS_IE)
+      && elf_x86_64_hash_entry (h)->tls_type == GOT_TLS_IE)
     {
       h->got.offset = (bfd_vma) -1;
     }
@@ -1977,7 +2121,7 @@ elf64_x86_64_allocate_dynrelocs (struct elf_link_hash_entry *h, void * inf)
     {
       asection *s;
       bfd_boolean dyn;
-      int tls_type = elf64_x86_64_hash_entry (h)->tls_type;
+      int tls_type = elf_x86_64_hash_entry (h)->tls_type;
 
       /* Make sure this symbol is output as a dynamic symbol.
         Undefined weak syms won't yet be marked as dynamic.  */
@@ -1991,7 +2135,7 @@ elf64_x86_64_allocate_dynrelocs (struct elf_link_hash_entry *h, void * inf)
       if (GOT_TLS_GDESC_P (tls_type))
        {
          eh->tlsdesc_got = htab->elf.sgotplt->size
-           - elf64_x86_64_compute_jump_table_size (htab);
+           - elf_x86_64_compute_jump_table_size (htab);
          htab->elf.sgotplt->size += 2 * GOT_ENTRY_SIZE;
          h->got.offset = (bfd_vma) -2;
        }
@@ -2010,18 +2154,18 @@ elf64_x86_64_allocate_dynrelocs (struct elf_link_hash_entry *h, void * inf)
         R_X86_64_GOTTPOFF needs one dynamic relocation.  */
       if ((GOT_TLS_GD_P (tls_type) && h->dynindx == -1)
          || tls_type == GOT_TLS_IE)
-       htab->elf.srelgot->size += sizeof (Elf64_External_Rela);
+       htab->elf.srelgot->size += bed->s->sizeof_rela;
       else if (GOT_TLS_GD_P (tls_type))
-       htab->elf.srelgot->size += 2 * sizeof (Elf64_External_Rela);
+       htab->elf.srelgot->size += 2 * bed->s->sizeof_rela;
       else if (! GOT_TLS_GDESC_P (tls_type)
               && (ELF_ST_VISIBILITY (h->other) == STV_DEFAULT
                   || h->root.type != bfd_link_hash_undefweak)
               && (info->shared
                   || WILL_CALL_FINISH_DYNAMIC_SYMBOL (dyn, 0, h)))
-       htab->elf.srelgot->size += sizeof (Elf64_External_Rela);
+       htab->elf.srelgot->size += bed->s->sizeof_rela;
       if (GOT_TLS_GDESC_P (tls_type))
        {
-         htab->elf.srelplt->size += sizeof (Elf64_External_Rela);
+         htab->elf.srelplt->size += bed->s->sizeof_rela;
          htab->tlsdesc_plt = (bfd_vma) -1;
        }
     }
@@ -2117,7 +2261,7 @@ elf64_x86_64_allocate_dynrelocs (struct elf_link_hash_entry *h, void * inf)
 
       BFD_ASSERT (sreloc != NULL);
 
-      sreloc->size += p->count * sizeof (Elf64_External_Rela);
+      sreloc->size += p->count * bed->s->sizeof_rela;
     }
 
   return TRUE;
@@ -2127,7 +2271,7 @@ elf64_x86_64_allocate_dynrelocs (struct elf_link_hash_entry *h, void * inf)
    local dynamic relocs.  */
 
 static bfd_boolean
-elf64_x86_64_allocate_local_dynrelocs (void **slot, void *inf)
+elf_x86_64_allocate_local_dynrelocs (void **slot, void *inf)
 {
   struct elf_link_hash_entry *h
     = (struct elf_link_hash_entry *) *slot;
@@ -2139,21 +2283,22 @@ elf64_x86_64_allocate_local_dynrelocs (void **slot, void *inf)
       || h->root.type != bfd_link_hash_defined)
     abort ();
 
-  return elf64_x86_64_allocate_dynrelocs (h, inf);
+  return elf_x86_64_allocate_dynrelocs (h, inf);
 }
 
 /* Find any dynamic relocs that apply to read-only sections.  */
 
 static bfd_boolean
-elf64_x86_64_readonly_dynrelocs (struct elf_link_hash_entry *h, void * inf)
+elf_x86_64_readonly_dynrelocs (struct elf_link_hash_entry *h,
+                              void * inf)
 {
-  struct elf64_x86_64_link_hash_entry *eh;
+  struct elf_x86_64_link_hash_entry *eh;
   struct elf_dyn_relocs *p;
 
   if (h->root.type == bfd_link_hash_warning)
     h = (struct elf_link_hash_entry *) h->root.u.i.link;
 
-  eh = (struct elf64_x86_64_link_hash_entry *) h;
+  eh = (struct elf_x86_64_link_hash_entry *) h;
   for (p = eh->dyn_relocs; p != NULL; p = p->next)
     {
       asection *s = p->sec->output_section;
@@ -2174,18 +2319,20 @@ elf64_x86_64_readonly_dynrelocs (struct elf_link_hash_entry *h, void * inf)
 /* Set the sizes of the dynamic sections.  */
 
 static bfd_boolean
-elf64_x86_64_size_dynamic_sections (bfd *output_bfd ATTRIBUTE_UNUSED,
-                                   struct bfd_link_info *info)
+elf_x86_64_size_dynamic_sections (bfd *output_bfd,
+                                 struct bfd_link_info *info)
 {
-  struct elf64_x86_64_link_hash_table *htab;
+  struct elf_x86_64_link_hash_table *htab;
   bfd *dynobj;
   asection *s;
   bfd_boolean relocs;
   bfd *ibfd;
+  const struct elf_backend_data *bed;
 
-  htab = elf64_x86_64_hash_table (info);
+  htab = elf_x86_64_hash_table (info);
   if (htab == NULL)
     return FALSE;
+  bed = get_elf_backend_data (output_bfd);
 
   dynobj = htab->elf.dynobj;
   if (dynobj == NULL)
@@ -2199,8 +2346,8 @@ elf64_x86_64_size_dynamic_sections (bfd *output_bfd ATTRIBUTE_UNUSED,
          s = bfd_get_section_by_name (dynobj, ".interp");
          if (s == NULL)
            abort ();
-         s->size = sizeof ELF_DYNAMIC_INTERPRETER;
-         s->contents = (unsigned char *) ELF_DYNAMIC_INTERPRETER;
+         s->size = htab->dynamic_interpreter_size;
+         s->contents = (unsigned char *) htab->dynamic_interpreter;
        }
     }
 
@@ -2239,7 +2386,7 @@ elf64_x86_64_size_dynamic_sections (bfd *output_bfd ATTRIBUTE_UNUSED,
              else if (p->count != 0)
                {
                  srel = elf_section_data (p->sec)->sreloc;
-                 srel->size += p->count * sizeof (Elf64_External_Rela);
+                 srel->size += p->count * bed->s->sizeof_rela;
                  if ((p->sec->output_section->flags & SEC_READONLY) != 0)
                    info->flags |= DF_TEXTREL;
                }
@@ -2253,8 +2400,8 @@ elf64_x86_64_size_dynamic_sections (bfd *output_bfd ATTRIBUTE_UNUSED,
       symtab_hdr = &elf_symtab_hdr (ibfd);
       locsymcount = symtab_hdr->sh_info;
       end_local_got = local_got + locsymcount;
-      local_tls_type = elf64_x86_64_local_got_tls_type (ibfd);
-      local_tlsdesc_gotent = elf64_x86_64_local_tlsdesc_gotent (ibfd);
+      local_tls_type = elf_x86_64_local_got_tls_type (ibfd);
+      local_tlsdesc_gotent = elf_x86_64_local_tlsdesc_gotent (ibfd);
       s = htab->elf.sgot;
       srel = htab->elf.srelgot;
       for (; local_got < end_local_got;
@@ -2266,7 +2413,7 @@ elf64_x86_64_size_dynamic_sections (bfd *output_bfd ATTRIBUTE_UNUSED,
              if (GOT_TLS_GDESC_P (*local_tls_type))
                {
                  *local_tlsdesc_gotent = htab->elf.sgotplt->size
-                   - elf64_x86_64_compute_jump_table_size (htab);
+                   - elf_x86_64_compute_jump_table_size (htab);
                  htab->elf.sgotplt->size += 2 * GOT_ENTRY_SIZE;
                  *local_got = (bfd_vma) -2;
                }
@@ -2285,12 +2432,12 @@ elf64_x86_64_size_dynamic_sections (bfd *output_bfd ATTRIBUTE_UNUSED,
                  if (GOT_TLS_GDESC_P (*local_tls_type))
                    {
                      htab->elf.srelplt->size
-                       += sizeof (Elf64_External_Rela);
+                       += bed->s->sizeof_rela;
                      htab->tlsdesc_plt = (bfd_vma) -1;
                    }
                  if (! GOT_TLS_GDESC_P (*local_tls_type)
                      || GOT_TLS_GD_P (*local_tls_type))
-                   srel->size += sizeof (Elf64_External_Rela);
+                   srel->size += bed->s->sizeof_rela;
                }
            }
          else
@@ -2304,19 +2451,19 @@ elf64_x86_64_size_dynamic_sections (bfd *output_bfd ATTRIBUTE_UNUSED,
         relocs.  */
       htab->tls_ld_got.offset = htab->elf.sgot->size;
       htab->elf.sgot->size += 2 * GOT_ENTRY_SIZE;
-      htab->elf.srelgot->size += sizeof (Elf64_External_Rela);
+      htab->elf.srelgot->size += bed->s->sizeof_rela;
     }
   else
     htab->tls_ld_got.offset = -1;
 
   /* Allocate global sym .plt and .got entries, and space for global
      sym dynamic relocs.  */
-  elf_link_hash_traverse (&htab->elf, elf64_x86_64_allocate_dynrelocs,
+  elf_link_hash_traverse (&htab->elf, elf_x86_64_allocate_dynrelocs,
                          info);
 
   /* Allocate .plt and .got entries, and space for local symbols.  */
   htab_traverse (htab->loc_hash_table,
-                elf64_x86_64_allocate_local_dynrelocs,
+                elf_x86_64_allocate_local_dynrelocs,
                 info);
 
   /* For every jump slot reserved in the sgotplt, reloc_count is
@@ -2326,7 +2473,7 @@ elf64_x86_64_size_dynamic_sections (bfd *output_bfd ATTRIBUTE_UNUSED,
      slot size.  */
   if (htab->elf.srelplt)
     htab->sgotplt_jump_table_size
-      = elf64_x86_64_compute_jump_table_size (htab);
+      = elf_x86_64_compute_jump_table_size (htab);
 
   if (htab->tlsdesc_plt)
     {
@@ -2347,6 +2494,30 @@ elf64_x86_64_size_dynamic_sections (bfd *output_bfd ATTRIBUTE_UNUSED,
        }
     }
 
+  if (htab->elf.sgotplt)
+    {
+      struct elf_link_hash_entry *got;
+      got = elf_link_hash_lookup (elf_hash_table (info),
+                                 "_GLOBAL_OFFSET_TABLE_",
+                                 FALSE, FALSE, FALSE);
+
+      /* Don't allocate .got.plt section if there are no GOT nor PLT
+         entries and there is no refeence to _GLOBAL_OFFSET_TABLE_.  */
+      if ((got == NULL
+          || !got->ref_regular_nonweak)
+         && (htab->elf.sgotplt->size
+             == get_elf_backend_data (output_bfd)->got_header_size)
+         && (htab->elf.splt == NULL
+             || htab->elf.splt->size == 0)
+         && (htab->elf.sgot == NULL
+             || htab->elf.sgot->size == 0)
+         && (htab->elf.iplt == NULL
+             || htab->elf.iplt->size == 0)
+         && (htab->elf.igotplt == NULL
+             || htab->elf.igotplt->size == 0))
+       htab->elf.sgotplt->size = 0;
+    }
+
   /* We now have determined the sizes of the various dynamic sections.
      Allocate memory for them.  */
   relocs = FALSE;
@@ -2413,7 +2584,7 @@ elf64_x86_64_size_dynamic_sections (bfd *output_bfd ATTRIBUTE_UNUSED,
   if (htab->elf.dynamic_sections_created)
     {
       /* Add some entries to the .dynamic section.  We fill in the
-        values later, in elf64_x86_64_finish_dynamic_sections, but we
+        values later, in elf_x86_64_finish_dynamic_sections, but we
         must add the entries now so that we get the correct size for
         the .dynamic section.  The DT_DEBUG entry is filled in by the
         dynamic linker and used by the debugger.  */
@@ -2444,14 +2615,14 @@ elf64_x86_64_size_dynamic_sections (bfd *output_bfd ATTRIBUTE_UNUSED,
        {
          if (!add_dynamic_entry (DT_RELA, 0)
              || !add_dynamic_entry (DT_RELASZ, 0)
-             || !add_dynamic_entry (DT_RELAENT, sizeof (Elf64_External_Rela)))
+             || !add_dynamic_entry (DT_RELAENT, bed->s->sizeof_rela))
            return FALSE;
 
          /* If any dynamic relocs apply to a read-only section,
             then we need a DT_TEXTREL entry.  */
          if ((info->flags & DF_TEXTREL) == 0)
            elf_link_hash_traverse (&htab->elf, 
-                                   elf64_x86_64_readonly_dynrelocs,
+                                   elf_x86_64_readonly_dynrelocs,
                                    info);
 
          if ((info->flags & DF_TEXTREL) != 0)
@@