diff options
author | Martin Schlemmer <azarah@gentoo.org> | 2003-06-28 12:37:27 +0000 |
---|---|---|
committer | Martin Schlemmer <azarah@gentoo.org> | 2003-06-28 12:37:27 +0000 |
commit | ae81827e1446e05b976c54119cd8c9687c5821a4 (patch) | |
tree | 909b77afd52c608e0f729d0829a3b27ebff1ecb5 /sys-devel | |
parent | Add patches from Redhat, as well as libtool fix. (diff) | |
download | historical-ae81827e1446e05b976c54119cd8c9687c5821a4.tar.gz historical-ae81827e1446e05b976c54119cd8c9687c5821a4.tar.bz2 historical-ae81827e1446e05b976c54119cd8c9687c5821a4.zip |
Add patches from Redhat, as well as libtool fix.
Diffstat (limited to 'sys-devel')
19 files changed, 6680 insertions, 19 deletions
diff --git a/sys-devel/binutils/Manifest b/sys-devel/binutils/Manifest index b0f7ceb91ced..fc4ac637cad6 100644 --- a/sys-devel/binutils/Manifest +++ b/sys-devel/binutils/Manifest @@ -3,7 +3,7 @@ MD5 011c5a33d84072e1af09ccf89cba6d61 binutils-2.11.92.0.7.ebuild 2357 MD5 368c85b995c3ab74a32a09e573aba1f9 binutils-2.12.90.0.15.ebuild 3512 MD5 fa1d184fbb7043a913d9307bd1b42fde binutils-2.12.90.0.7.ebuild 3594 MD5 5ed1c40a92233028ce782a0c337603d9 binutils-2.13.90.0.16-r1.ebuild 4740 -MD5 be1cfb5ac654610acf7699670c146395 ChangeLog 11112 +MD5 bca9da39cbabf681277db2f951736014 ChangeLog 12102 MD5 2adeb2860e4df3cdcb96ef6cd5430ab1 binutils-2.13.90.0.18-r1.ebuild 5376 MD5 51bfea19ab266367baf39b3e6224be33 binutils-2.13.90.0.18.ebuild 4580 MD5 7a3bbb04c9a5243c92f1d972cb0b61ec binutils-2.13.90.0.20-r1.ebuild 5001 @@ -11,8 +11,7 @@ MD5 2e588e007eb122eb471c48aefcb04a41 binutils-2.14.90.0.1-r1.ebuild 5097 MD5 f6f5a7b9dacfa66f84d1558b2cf96612 binutils-2.14.90.0.2.ebuild 4846 MD5 e7df35e2bb31fb0268d2150da19b27b9 binutils-2.14.90.0.4.ebuild 4842 MD5 8303a09e50b83d864db0735fd00cf7bd binutils-2.14.90.0.4.1.ebuild 4851 -MD5 ce37883fe7ecfb6462e0c8ead8e6364b binutils-2.14.90.0.4.1-r1.ebuild 5611 -MD5 32c67690b25b2358a306ee0dafbe435f .binutils-2.14.90.0.4.1-r1.ebuild.swp 20480 +MD5 1d389cd4bba4bec258e3fbc120f6160f binutils-2.14.90.0.4.1-r1.ebuild 5808 MD5 fe5fb935b171a472f5eb1a8bca63c136 files/binutils-2.12.90.0.14-glibc21.patch 7936 MD5 f453b3f208b17cd18380bc3653936487 files/binutils-2.12.90.0.14-x86_64-libpic.patch 1184 MD5 db3f89b51f6961b0cf92bdddf8127ea7 files/digest-binutils-2.11.92.0.12.3-r2 161 @@ -59,19 +58,19 @@ MD5 2183b775b86400dd7eda35bf1ccee678 files/2.13/binutils-2.13.90.0.20-gas-mips-g MD5 c98edbd5a87f00832a367a40a6e576d1 files/2.14/binutils-2.14.90.0.1-eh-frame-ro.patch 17942 MD5 e941bf2e41367989d389e2988672f87a files/2.14/binutils-2.14.90.0.1-sparc-nonpic.patch 3147 MD5 03d6c934577cf40ec75b41bfc38b48a0 files/2.14/binutils-mips-openssl-got-fix.patch 540 -MD5 d232bcf016de028994efd262aa2ff401 files/2.14/new/binutils-2.14.90.0.4-cfi.patch 74784 -MD5 e7283a4967ce5101a016b31e747e8442 files/2.14/new/binutils-2.14.90.0.4-cfi2.patch 18449 -MD5 42ecd945c2269a792b9b7aea542b9a16 files/2.14/new/binutils-2.14.90.0.4-cfi3.patch 13929 -MD5 613770b55db9f6e3c11f040a94c9c4ea files/2.14/new/binutils-2.14.90.0.4-cfi4.patch 11909 -MD5 04ed3642c4bebee3fe6de9e9e6e2f23b files/2.14/new/binutils-2.14.90.0.4-eh-frame-ro.patch 16503 -MD5 60ff948d89725566178e8149375c3f31 files/2.14/new/binutils-2.14.90.0.4-gas-execstack.patch 3379 -MD5 69161dd93a78ddede56256e0de28d282 files/2.14/new/binutils-2.14.90.0.4-gas-pred.patch 1104 -MD5 fed0711b95edc0c64ee93ccfbc8e6268 files/2.14/new/binutils-2.14.90.0.4-ltconfig-multilib.patch 878 -MD5 ee0529757cf72b4d4f8c30733cda49c7 files/2.14/new/binutils-2.14.90.0.4-pie.patch 24448 -MD5 3793ff770ff2fca80a2238f8de0a165e files/2.14/new/binutils-2.14.90.0.4-pie2.patch 1011 -MD5 4aa97425036b8c3fb98975ab06cab3ae files/2.14/new/binutils-2.14.90.0.4-pni.patch 16030 -MD5 b42bde8fcae8815f106b6c1f78e68134 files/2.14/new/binutils-2.14.90.0.4-ppc-bigplt.patch 628 -MD5 f8d0738db8174c369f4f3a6185d8f76b files/2.14/new/binutils-2.14.90.0.4-ppc64-ctors.patch 843 -MD5 5fa7bd6f7e2c4fa50b74367a85f37541 files/2.14/new/binutils-2.14.90.0.4-ppc64-prelink.patch 4721 -MD5 e6f5f65fe3a3998c3c2845b92eef79e8 files/2.14/new/binutils-2.14.90.0.4-pt-gnu-stack.patch 8453 -MD5 e941bf2e41367989d389e2988672f87a files/2.14/new/binutils-2.14.90.0.4-sparc-nonpic.patch 3147 +MD5 d232bcf016de028994efd262aa2ff401 files/2.14/binutils-2.14.90.0.4-cfi.patch 74784 +MD5 e7283a4967ce5101a016b31e747e8442 files/2.14/binutils-2.14.90.0.4-cfi2.patch 18449 +MD5 42ecd945c2269a792b9b7aea542b9a16 files/2.14/binutils-2.14.90.0.4-cfi3.patch 13929 +MD5 613770b55db9f6e3c11f040a94c9c4ea files/2.14/binutils-2.14.90.0.4-cfi4.patch 11909 +MD5 04ed3642c4bebee3fe6de9e9e6e2f23b files/2.14/binutils-2.14.90.0.4-eh-frame-ro.patch 16503 +MD5 60ff948d89725566178e8149375c3f31 files/2.14/binutils-2.14.90.0.4-gas-execstack.patch 3379 +MD5 69161dd93a78ddede56256e0de28d282 files/2.14/binutils-2.14.90.0.4-gas-pred.patch 1104 +MD5 fed0711b95edc0c64ee93ccfbc8e6268 files/2.14/binutils-2.14.90.0.4-ltconfig-multilib.patch 878 +MD5 ee0529757cf72b4d4f8c30733cda49c7 files/2.14/binutils-2.14.90.0.4-pie.patch 24448 +MD5 3793ff770ff2fca80a2238f8de0a165e files/2.14/binutils-2.14.90.0.4-pie2.patch 1011 +MD5 4aa97425036b8c3fb98975ab06cab3ae files/2.14/binutils-2.14.90.0.4-pni.patch 16030 +MD5 b42bde8fcae8815f106b6c1f78e68134 files/2.14/binutils-2.14.90.0.4-ppc-bigplt.patch 628 +MD5 f8d0738db8174c369f4f3a6185d8f76b files/2.14/binutils-2.14.90.0.4-ppc64-ctors.patch 843 +MD5 5fa7bd6f7e2c4fa50b74367a85f37541 files/2.14/binutils-2.14.90.0.4-ppc64-prelink.patch 4721 +MD5 e6f5f65fe3a3998c3c2845b92eef79e8 files/2.14/binutils-2.14.90.0.4-pt-gnu-stack.patch 8453 +MD5 e941bf2e41367989d389e2988672f87a files/2.14/binutils-2.14.90.0.4-sparc-nonpic.patch 3147 diff --git a/sys-devel/binutils/binutils-2.14.90.0.4.1-r1.ebuild b/sys-devel/binutils/binutils-2.14.90.0.4.1-r1.ebuild new file mode 100644 index 000000000000..93d2adbb5093 --- /dev/null +++ b/sys-devel/binutils/binutils-2.14.90.0.4.1-r1.ebuild @@ -0,0 +1,192 @@ +# Copyright 1999-2003 Gentoo Technologies, Inc. +# Distributed under the terms of the GNU General Public License v2 +# $Header: /var/cvsroot/gentoo-x86/sys-devel/binutils/binutils-2.14.90.0.4.1-r1.ebuild,v 1.1 2003/06/28 12:35:44 azarah Exp $ + +IUSE="nls bootstrap build" + +# NOTE to Maintainer: ChangeLog states that it no longer use perl to build +# the manpages, but seems this is incorrect .... + +inherit eutils libtool flag-o-matic + +# Generate borked binaries. Bug #6730 +filter-flags "-fomit-frame-pointer -fssa" + +S="${WORKDIR}/${P}" +DESCRIPTION="Tools necessary to build programs" +SRC_URI="mirror://kernel/linux/devel/binutils/${P}.tar.bz2 + mirror://kernel/linux/devel/binutils/test/${P}.tar.bz2" +HOMEPAGE="http://sources.redhat.com/binutils/" + +SLOT="0" +LICENSE="GPL-2 | LGPL-2" +KEYWORDS="~amd64 -x86 -ppc -alpha -sparc -mips -hppa -arm" + +DEPEND="virtual/glibc + >=sys-apps/portage-2.0.21 + nls? ( sys-devel/gettext ) + || ( dev-lang/perl + ( !build? ( dev-lang/perl ) ) + ( !bootstrap? ( dev-lang/perl ) ) + )" +# This is a hairy one. Basically depend on dev-lang/perl +# if "build" or "bootstrap" not in USE. + + +# filter CFLAGS=".. -O2 .." on arm +if [ "${ARCH}" = "arm" ]; then + CFLAGS="$(echo "${CFLAGS}" | sed -e 's,-O[2-9] ,-O1 ,')" +fi + +src_unpack() { + + unpack ${A} + + cd ${S} + epatch ${FILESDIR}/2.13/${PN}-2.13.90.0.10-glibc21.patch + epatch ${FILESDIR}/2.14/${PN}-2.14.90.0.4-sparc-nonpic.patch + epatch ${FILESDIR}/2.14/${PN}-2.14.90.0.4-eh-frame-ro.patch + epatch ${FILESDIR}/2.14/${PN}-2.14.90.0.4-ltconfig-multilib.patch + epatch ${FILESDIR}/2.14/${PN}-2.14.90.0.4-cfi.patch + epatch ${FILESDIR}/2.14/${PN}-2.14.90.0.4-pie.patch + epatch ${FILESDIR}/2.14/${PN}-2.14.90.0.4-ppc-bigplt.patch + epatch ${FILESDIR}/2.14/${PN}-2.14.90.0.4-pt-gnu-stack.patch + epatch ${FILESDIR}/2.14/${PN}-2.14.90.0.4-gas-execstack.patch + epatch ${FILESDIR}/2.14/${PN}-2.14.90.0.4-cfi2.patch + epatch ${FILESDIR}/2.14/${PN}-2.14.90.0.4-pie2.patch + epatch ${FILESDIR}/2.14/${PN}-2.14.90.0.4-ppc64-ctors.patch + epatch ${FILESDIR}/2.14/${PN}-2.14.90.0.4-ppc64-prelink.patch + epatch ${FILESDIR}/2.14/${PN}-2.14.90.0.4-cfi3.patch + epatch ${FILESDIR}/2.14/${PN}-2.14.90.0.4-cfi4.patch + epatch ${FILESDIR}/2.14/${PN}-2.14.90.0.4-gas-pred.patch + epatch ${FILESDIR}/2.14/${PN}-2.14.90.0.4-pni.patch + epatch ${FILESDIR}/2.13/${PN}-2.13.90.0.10-x86_64-testsuite.patch + epatch ${FILESDIR}/2.13/${PN}-2.13.90.0.10-x86_64-gotpcrel.patch + epatch ${FILESDIR}/2.13/${PN}-2.13.90.0.18-s390-file-loc.patch + epatch ${FILESDIR}/2.13/${PN}-2.13.90.0.18-testsuite-Wall-fixes.patch + + use x86 &> /dev/null \ + && epatch ${FILESDIR}/2.13/${PN}-2.13.90.0.20-array-sects-compat.patch + + # Fixes a MIPS issue in which the dynamic relocation table in OpenSSL libs + # gets broken because the GOT entry count is too low + if [ "${ARCH}" = "mips" ]; then + epatch ${FILESDIR}/2.14/${PN}-mips-openssl-got-fix.patch + fi + + # Libtool is broken (Redhat). + for x in ${S}/opcodes/Makefile.{am,in} + do + cp ${x} ${x}.orig + gawk ' + { + if ($0 ~ /LIBADD/) + gsub("../bfd/libbfd.la", "-L../bfd/.libs ../bfd/libbfd.la") + + print + }' ${x}.orig > ${x} + rm -rf ${x}.orig + done +} + +src_compile() { + local myconf= + + use nls && \ + myconf="${myconf} --without-included-gettext" || \ + myconf="${myconf} --disable-nls" + + # Fix /usr/lib/libbfd.la + elibtoolize --portage + + ./configure --enable-shared \ + --enable-64-bit-bfd \ + --prefix=/usr \ + --mandir=/usr/share/man \ + --infodir=/usr/share/info \ + --host=${CHOST} \ + ${myconf} || die + + make configure-bfd || die + make headers -C bfd || die + emake tooldir="${ROOT}/usr/bin" \ + all || die + + if [ -z "`use build`" ] + then + if [ -z "`use bootstrap`" ] + then + # Nuke the manpages to recreate them (only use this if we have perl) + find . -name '*.1' -exec rm -f {} \; || : + fi + # Make the info pages (makeinfo included with gcc is used) + make info || die + fi +} + +src_install() { + + make prefix=${D}/usr \ + mandir=${D}/usr/share/man \ + infodir=${D}/usr/share/info \ + install || die + + insinto /usr/include + doins include/libiberty.h + + # c++filt is included with gcc -- what are these GNU people thinking? + # but not the manpage, so leave that! +# We install it now, as gcc-3.3 do not have it any longer ... +# rm -f ${D}/usr/bin/c++filt #${D}/usr/share/man/man1/c++filt* + + # By default strip has a symlink going from /usr/${CHOST}/bin/strip to + # /usr/bin/strip we should reverse it: + + rm ${D}/usr/${CHOST}/bin/strip; mv ${D}/usr/bin/strip ${D}/usr/${CHOST}/bin/strip + # The strip symlink gets created in the loop below + + # By default ar, as, ld, nm, ranlib and strip are in two places; create + # symlinks. This will reduce the size of the tbz2 significantly. We also + # move all the stuff in /usr/bin to /usr/${CHOST}/bin and create the + # appropriate symlinks. Things are cleaner that way. + cd ${D}/usr/bin + local x= + for x in * strip + do + if [ ! -e ../${CHOST}/bin/${x} ] + then + mv ${x} ../${CHOST}/bin/${x} + else + rm -f ${x} + fi + ln -s ../${CHOST}/bin/${x} ${x} + done + + cd ${S} + if [ -z "`use build`" ] + then + make prefix=${D}/usr \ + mandir=${D}/usr/share/man \ + infodir=${D}/usr/share/info \ + install-info || die + + dodoc COPYING* README + docinto bfd + dodoc bfd/ChangeLog* bfd/COPYING bfd/README bfd/PORTING bfd/TODO + docinto binutils + dodoc binutils/ChangeLog binutils/NEWS binutils/README + docinto gas + dodoc gas/ChangeLog* gas/CONTRIBUTORS gas/COPYING gas/NEWS gas/README* + docinto gprof + dodoc gprof/ChangeLog* gprof/TEST gprof/TODO + docinto ld + dodoc ld/ChangeLog* ld/README ld/NEWS ld/TODO + docinto libiberty + dodoc libiberty/ChangeLog* libiberty/COPYING.LIB libiberty/README + docinto opcodes + dodoc opcodes/ChangeLog* + # Install pre-generated manpages .. currently we do not ... + else + rm -rf ${D}/usr/share/man + fi +} diff --git a/sys-devel/binutils/files/2.14/binutils-2.14.90.0.4-cfi.patch b/sys-devel/binutils/files/2.14/binutils-2.14.90.0.4-cfi.patch new file mode 100644 index 000000000000..e8e6250c4ef2 --- /dev/null +++ b/sys-devel/binutils/files/2.14/binutils-2.14.90.0.4-cfi.patch @@ -0,0 +1,2690 @@ +2003-06-02 Alan Modra <amodra@bigpond.net.au> + + * read.c (emit_expr): Set dot_value. + * dw2gencfi.c (output_fde): Remove pcrel reloc hack. + +2003-06-02 Alan Modra <amodra@bigpond.net.au> + + * macro.c (sub_actual): Don't lose string if it turns out that + &string wasn't an arg. + +2003-05-31 Richard Henderson <rth@redhat.com> + + * dw2gencfi.c (output_fde): Use fix_new to emit pc-relative reloc. + (cfi_finish): Set flag_traditional_format around .eh_frame data. + +2003-05-29 Richard Henderson <rth@redhat.com> + + * config/tc-alpha.c (alpha_cur_ent_sym): Remove. + (all_frame_data, plast_frame_data, cur_frame_data): New. + (s_alpha_ent): Record data for dwarf2 cfi. + (s_alpha_end, s_alpha_mask, s_alpha_frame, s_alpha_prologue): Likewise. + (alpha_elf_md_end): Emit dwarf2 cfi for ecoff unwind directives. + * config/tc-alpha.h (md_end): New. + (DWARF2_DEFAULT_RETURN_COLUMN): New. + (DWARF2_CIE_DATA_ALIGNMENT): New. + +2003-05-27 Richard Henderson <rth@redhat.com> + + * expr.c (make_expr_symbol): Fold FAKE_LABEL_NAME use into the + symbol_create call. + (current_location): Use symbol_temp_new_now. + * stabs.c (s_stab_generic): Use symbol_temp_new. + * symbols.c (temp_label_name): Remove. + (symbol_temp_new, symbol_temp_make): Use FAKE_LABEL_NAME. + +2003-05-27 Richard Henderson <rth@redhat.com> + + * dw2gencfi.c, dw2gencfi.h: Rewrite from scratch. + * as.c (main): Always call cfi_finish. + * config/tc-i386.c (x86_dwarf2_return_column): New. + (x86_cie_data_alignment): New. + (md_begin): Set them. + (tc_x86_cfi_init): Remove. + (tc_x86_regname_to_dw2regnum): Fix 32-bit register numbers; + return int, not unsigned long; don't as_bad here. + (tc_x86_frame_initial_instructions): Streamline; use + updated api. + * config/tc-i386.h (tc_cfi_init): Remove. + (DWARF2_DEFAULT_RETURN_COLUMN): New. + (DWARF2_CIE_DATA_ALIGNMENT): New. + +2003-05-27 Richard Henderson <rth@redhat.com> + + * symbols.c (temp_label_name): New. + (symbol_temp_new, symbol_temp_new_now, symbol_temp_make): New. + (symbol_set_value_now): New. + * symbols.h: Prototype them. + * dwarf2dbg.c: Use them. + (fake_label_name, symbol_new_now, set_symbol_value_now): Remove. + +testsuite/ +2003-05-31 Richard Henderson <rth@redhat.com> + + * gas/alpha/elf-reloc-8.d: Correct .eh_frame relocs. + * gas/cfi/cfi-alpha-2.d: New. + * gas/cfi/cfi-alpha-2.s: New. + * gas/cfi/cfi.exp: Run it. + +2003-05-29 Richard Henderson <rth@redhat.com> + + * gas/alpha/elf-reloc-8.d: Add .eh_frame relocs. + * gas/cfi/cfi-alpha-1.d: New. + * gas/cfi/cfi-alpha-1.s: New. + * gas/cfi/cfi.exp: Run it. + +2003-05-27 Richard Henderson <rth@redhat.com> + + * gas/cfi/cfi-i386.d: Update for dw2gencfi rewrite. + * gas/cfi/cfi-x86_64.d: Likewise. + * gas/cfi/cfi-i386-2.d: New. + * gas/cfi/cfi-i386-2.s: New. + +--- gas/as.c 20 May 2003 14:31:44 -0000 1.44 ++++ gas/as.c 27 May 2003 16:52:46 -0000 1.45 +@@ -911,9 +911,9 @@ main (argc, argv) + assembly debugging or on behalf of the compiler, emit it now. */ + dwarf2_finish (); + +-#ifdef TARGET_USE_CFIPOP ++ /* If we constructed dwarf2 .eh_frame info, either via .cfi ++ directives from the user or by the backend, emit it now. */ + cfi_finish (); +-#endif + + if (seen_at_least_1_file () + && (flag_always_generate_output || had_errors () == 0)) +--- gas/dw2gencfi.c 21 May 2003 11:31:07 -0000 1.4 ++++ gas/dw2gencfi.c 2 Jun 2003 22:48:59 -0000 1.7 +@@ -19,812 +19,789 @@ + Software Foundation, 59 Temple Place - Suite 330, Boston, MA + 02111-1307, USA. */ + +-#include <errno.h> + #include "as.h" + #include "dw2gencfi.h" + +-struct cie_entry ++ ++/* We re-use DWARF2_LINE_MIN_INSN_LENGTH for the code alignment field ++ of the CIE. Default to 1 if not otherwise specified. */ ++#ifndef DWARF2_LINE_MIN_INSN_LENGTH ++# define DWARF2_LINE_MIN_INSN_LENGTH 1 ++#endif ++ ++/* If TARGET_USE_CFIPOP is defined, it is required that the target ++ provide the following definitions. Otherwise provide them to ++ allow compilation to continue. */ ++#ifndef TARGET_USE_CFIPOP ++# ifndef DWARF2_DEFAULT_RETURN_COLUMN ++# define DWARF2_DEFAULT_RETURN_COLUMN 0 ++# endif ++# ifndef DWARF2_CIE_DATA_ALIGNMENT ++# define DWARF2_CIE_DATA_ALIGNMENT 1 ++# endif ++#endif ++ ++#ifndef tc_cfi_frame_initial_instructions ++# define tc_cfi_frame_initial_instructions() ((void)0) ++#endif ++ ++ ++struct cfi_insn_data + { +- unsigned long offset; +- size_t size; +- void *data; +- struct cie_entry *next; ++ struct cfi_insn_data *next; ++ int insn; ++ union { ++ struct { ++ unsigned reg; ++ offsetT offset; ++ } ri; ++ ++ struct { ++ unsigned reg1; ++ unsigned reg2; ++ } rr; ++ ++ unsigned r; ++ offsetT i; ++ ++ struct { ++ symbolS *lab1; ++ symbolS *lab2; ++ } ll; ++ } u; + }; + +-struct cfi_data ++struct fde_entry + { +- enum cfi_insn insn; +- long param[2]; +- struct cfi_data *next; ++ struct fde_entry *next; ++ symbolS *start_address; ++ symbolS *end_address; ++ struct cfi_insn_data *data; ++ struct cfi_insn_data **last; ++ unsigned int return_column; + }; + +-struct cfi_info ++struct cie_entry + { +- addressT start_address; +- addressT end_address; +- addressT last_address; +- const char *labelname; +- struct cfi_data *data; +- struct cfi_info *next; ++ struct cie_entry *next; ++ symbolS *start_address; ++ unsigned int return_column; ++ struct cfi_insn_data *first, *last; + }; + +-/* Current open CFI entry. */ +-static struct cfi_info *cfi_info; ++ ++/* Current open FDE entry. */ ++static struct fde_entry *cur_fde_data; ++static symbolS *last_address; ++static offsetT cur_cfa_offset; ++ ++/* List of FDE entries. */ ++static struct fde_entry *all_fde_data; ++static struct fde_entry **last_fde_data = &all_fde_data; + + /* List of CIEs so that they could be reused. */ + static struct cie_entry *cie_root; + +-/* Current target config. */ +-static struct cfi_config current_config; ++ ++/* Construct a new FDE structure and add it to the end of the fde list. */ + +-/* This is the main entry point to the CFI machinery. */ +-static void dot_cfi (int arg); ++static struct fde_entry * ++alloc_fde_entry (void) ++{ ++ struct fde_entry *fde = xcalloc (1, sizeof (struct fde_entry)); + +-const pseudo_typeS cfi_pseudo_table[] = +- { +- { "cfi_verbose", dot_cfi, CFI_verbose }, +- { "cfi_startproc", dot_cfi, CFI_startproc }, +- { "cfi_endproc", dot_cfi, CFI_endproc }, +- { "cfi_def_cfa", dot_cfi, CFA_def_cfa }, +- { "cfi_def_cfa_register", dot_cfi, CFA_def_cfa_register }, +- { "cfi_def_cfa_offset", dot_cfi, CFA_def_cfa_offset }, +- { "cfi_adjust_cfa_offset", dot_cfi, CFI_adjust_cfa_offset }, +- { "cfi_offset", dot_cfi, CFA_offset }, +- { "cfi_register", dot_cfi, CFA_register }, +- { NULL, NULL, 0 } +- }; ++ cur_fde_data = fde; ++ *last_fde_data = fde; ++ last_fde_data = &fde->next; ++ ++ fde->last = &fde->data; ++ fde->return_column = DWARF2_DEFAULT_RETURN_COLUMN; ++ ++ return fde; ++} ++ ++/* The following functions are available for a backend to construct its ++ own unwind information, usually from legacy unwind directives. */ ++ ++/* Construct a new INSN structure and add it to the end of the insn list ++ for the currently active FDE. */ + +-static const char * +-cfi_insn_str (enum cfi_insn insn) ++static struct cfi_insn_data * ++alloc_cfi_insn_data (void) + { +- switch (insn) +- { +- case CFA_nop: +- return "CFA_nop"; +- case CFA_set_loc: +- return "CFA_set_loc"; +- case CFA_advance_loc1: +- return "CFA_advance_loc1"; +- case CFA_advance_loc2: +- return "CFA_advance_loc2"; +- case CFA_advance_loc4: +- return "CFA_advance_loc4"; +- case CFA_offset_extended: +- return "CFA_offset_extended"; +- case CFA_resotre_extended: +- return "CFA_resotre_extended"; +- case CFA_undefined: +- return "CFA_undefined"; +- case CFA_same_value: +- return "CFA_same_value"; +- case CFA_register: +- return "CFA_register"; +- case CFA_remember_state: +- return "CFA_remember_state"; +- case CFA_restore_state: +- return "CFA_restore_state"; +- case CFA_def_cfa: +- return "CFA_def_cfa"; +- case CFA_def_cfa_register: +- return "CFA_def_cfa_register"; +- case CFA_def_cfa_offset: +- return "CFA_def_cfa_offset"; +- case CFA_advance_loc: +- return "CFA_advance_loc"; +- case CFA_offset: +- return "CFA_offset"; +- case CFA_restore: +- return "CFA_restore"; +- default: +- break; +- } ++ struct cfi_insn_data *insn = xcalloc (1, sizeof (struct cfi_insn_data)); + +- return "CFA_unknown"; ++ *cur_fde_data->last = insn; ++ cur_fde_data->last = &insn->next; ++ ++ return insn; + } + +-static struct cfi_data * +-alloc_cfi_data (void) ++/* Construct a new FDE structure that begins at LABEL. */ ++ ++void ++cfi_new_fde (symbolS *label) + { +- return (struct cfi_data *) xcalloc (sizeof (struct cfi_info), 1); ++ struct fde_entry *fde = alloc_fde_entry (); ++ fde->start_address = label; ++ last_address = label; + } + +-static struct cfi_info * +-alloc_cfi_info (void) ++/* End the currently open FDE. */ ++ ++void ++cfi_end_fde (symbolS *label) + { +- return (struct cfi_info *) xcalloc (sizeof (struct cfi_info), 1); ++ cur_fde_data->end_address = label; ++ cur_fde_data = NULL; + } + +-/* Parse arguments. */ +-static int +-cfi_parse_arg (long *param, int resolvereg) ++/* Set the return column for the current FDE. */ ++ ++void ++cfi_set_return_column (unsigned regno) + { +- long value; +- int retval = -1; +- int nchars; ++ cur_fde_data->return_column = regno; ++} + +- assert (param != NULL); +- SKIP_WHITESPACE (); ++/* Add a CFI insn to advance the PC from the last address to LABEL. */ + +- if (sscanf (input_line_pointer, "%li%n", &value, &nchars) >= 1) +- { +- input_line_pointer += nchars; +- retval = 1; +- } +-#ifdef tc_regname_to_dw2regnum +- else if (resolvereg && ((is_name_beginner (*input_line_pointer)) +- || (*input_line_pointer == '%' +- && is_name_beginner (*(++input_line_pointer))))) +- { +- char *name, c, *p; ++void ++cfi_add_advance_loc (symbolS *label) ++{ ++ struct cfi_insn_data *insn = alloc_cfi_insn_data (); + +- name = input_line_pointer; +- c = get_symbol_end (); +- p = input_line_pointer; ++ insn->insn = DW_CFA_advance_loc; ++ insn->u.ll.lab1 = last_address; ++ insn->u.ll.lab2 = label; ++ ++ last_address = label; ++} + +- if ((value = tc_regname_to_dw2regnum (name)) >= 0) +- retval = 1; ++/* Add a DW_CFA_offset record to the CFI data. */ + +- *p = c; +- } +-#endif +- else +- as_bad (resolvereg ? +- _("can't convert argument to a register number") : +- _("can't convert argument to an integer")); ++void ++cfi_add_CFA_offset (unsigned regno, offsetT offset) ++{ ++ struct cfi_insn_data *insn = alloc_cfi_insn_data (); ++ ++ insn->insn = DW_CFA_offset; ++ insn->u.ri.reg = regno; ++ insn->u.ri.offset = offset; ++} + +- if (retval > 0) +- *param = value; ++/* Add a DW_CFA_def_cfa record to the CFI data. */ + +- SKIP_WHITESPACE (); +- if (*input_line_pointer == ',') +- { +- input_line_pointer++; +- SKIP_WHITESPACE (); +- } ++void ++cfi_add_CFA_def_cfa (unsigned regno, offsetT offset) ++{ ++ struct cfi_insn_data *insn = alloc_cfi_insn_data (); ++ ++ insn->insn = DW_CFA_def_cfa; ++ insn->u.ri.reg = regno; ++ insn->u.ri.offset = offset; + +- return retval; ++ cur_cfa_offset = offset; + } + +-static int +-cfi_parse_reg (long *param) ++/* Add a DW_CFA_register record to the CFI data. */ ++ ++void ++cfi_add_CFA_register (unsigned reg1, unsigned reg2) + { +- return cfi_parse_arg (param, 1); ++ struct cfi_insn_data *insn = alloc_cfi_insn_data (); ++ ++ insn->insn = DW_CFA_register; ++ insn->u.rr.reg1 = reg1; ++ insn->u.rr.reg2 = reg2; + } + +-static int +-cfi_parse_const (long *param) ++/* Add a DW_CFA_def_cfa_register record to the CFI data. */ ++ ++void ++cfi_add_CFA_def_cfa_register (unsigned regno) + { +- return cfi_parse_arg (param, 0); ++ struct cfi_insn_data *insn = alloc_cfi_insn_data (); ++ ++ insn->insn = DW_CFA_def_cfa_register; ++ insn->u.r = regno; + } + ++/* Add a DW_CFA_def_cfa_offset record to the CFI data. */ ++ + void +-cfi_add_insn (enum cfi_insn insn, long param0, long param1) ++cfi_add_CFA_def_cfa_offset (offsetT offset) + { +- struct cfi_data *data_ptr; ++ struct cfi_insn_data *insn = alloc_cfi_insn_data (); ++ ++ insn->insn = DW_CFA_def_cfa_offset; ++ insn->u.i = offset; + +- if (!cfi_info->data) +- { +- cfi_info->data = alloc_cfi_data (); +- data_ptr = cfi_info->data; +- } +- else +- { +- data_ptr = cfi_info->data; ++ cur_cfa_offset = offset; ++} + +- while (data_ptr && data_ptr->next) +- data_ptr = data_ptr->next; ++ ++/* Parse CFI assembler directives. */ + +- data_ptr->next = alloc_cfi_data (); ++static void dot_cfi (int); ++static void dot_cfi_startproc (int); ++static void dot_cfi_endproc (int); + +- data_ptr = data_ptr->next; +- } ++/* Fake CFI type; outside the byte range of any real CFI insn. */ ++#define CFI_adjust_cfa_offset 0x100 + +- data_ptr->insn = insn; +- data_ptr->param[0] = param0; +- data_ptr->param[1] = param1; +-} ++const pseudo_typeS cfi_pseudo_table[] = ++ { ++ { "cfi_startproc", dot_cfi_startproc, 0 }, ++ { "cfi_endproc", dot_cfi_endproc, 0 }, ++ { "cfi_def_cfa", dot_cfi, DW_CFA_def_cfa }, ++ { "cfi_def_cfa_register", dot_cfi, DW_CFA_def_cfa_register }, ++ { "cfi_def_cfa_offset", dot_cfi, DW_CFA_def_cfa_offset }, ++ { "cfi_adjust_cfa_offset", dot_cfi, CFI_adjust_cfa_offset }, ++ { "cfi_offset", dot_cfi, DW_CFA_offset }, ++ { "cfi_register", dot_cfi, DW_CFA_register }, ++ { NULL, NULL, 0 } ++ }; + + static void +-cfi_advance_loc (void) ++cfi_parse_separator (void) + { +- addressT curr_address = frag_now_fix (); +- if (cfi_info->last_address == curr_address) +- return; +- cfi_add_insn (CFA_advance_loc, +- (long) (curr_address - cfi_info->last_address), 0); +- cfi_info->last_address = curr_address; ++ SKIP_WHITESPACE (); ++ if (*input_line_pointer == ',') ++ input_line_pointer++; ++ else ++ as_bad (_("missing separator")); + } + +-static long +-get_current_offset (struct cfi_info *info) ++static unsigned ++cfi_parse_reg (void) + { +- long current_offset = 0; +- struct cfi_data *data = info->data; ++ int regno; ++ expressionS exp; ++ ++#ifdef tc_regname_to_dw2regnum ++ SKIP_WHITESPACE (); ++ if (is_name_beginner (*input_line_pointer) ++ || (*input_line_pointer == '%' ++ && is_name_beginner (*++input_line_pointer))) ++ { ++ char *name, c; ++ ++ name = input_line_pointer; ++ c = get_symbol_end (); ++ ++ if ((regno = tc_regname_to_dw2regnum (name)) < 0) ++ { ++ as_bad (_("bad register expression")); ++ regno = 0; ++ } ++ ++ *input_line_pointer = c; ++ return regno; ++ } ++#endif + +- current_offset = 0; +- while (data) ++ expression (&exp); ++ switch (exp.X_op) + { +- if (data->insn == CFA_def_cfa) +- current_offset = data->param[1]; +- else if (data->insn == CFA_def_cfa_offset) +- current_offset = data->param[0]; +- data = data->next; ++ case O_register: ++ case O_constant: ++ regno = exp.X_add_number; ++ break; ++ ++ default: ++ as_bad (_("bad register expression")); ++ regno = 0; ++ break; + } + +- return current_offset; ++ return regno; ++} ++ ++static offsetT ++cfi_parse_const (void) ++{ ++ return get_absolute_expression (); + } + + static void +-cfi_make_insn (int arg) ++dot_cfi (int arg) + { +- long param[2] = { 0, 0 }; ++ offsetT offset; ++ unsigned reg1, reg2; + +- if (!cfi_info) ++ if (!cur_fde_data) + { + as_bad (_("CFI instruction used without previous .cfi_startproc")); + return; + } + +- cfi_advance_loc (); ++ /* If the last address was not at the current PC, advance to current. */ ++ if (symbol_get_frag (last_address) != frag_now ++ || S_GET_VALUE (last_address) != frag_now_fix ()) ++ cfi_add_advance_loc (symbol_temp_new_now ()); + + switch (arg) + { + /* Instructions that take two arguments (register, integer). */ +- case CFA_offset: +- case CFA_def_cfa: +- if (cfi_parse_reg (¶m[0]) < 0) +- { +- as_bad (_("first argument to %s is not a register"), +- cfi_insn_str (arg)); +- return; +- } +- if (cfi_parse_const (¶m[1]) < 0) +- { +- as_bad (_("second argument to %s is not a number"), +- cfi_insn_str (arg)); +- return; +- } ++ case DW_CFA_offset: ++ case DW_CFA_def_cfa: ++ reg1 = cfi_parse_reg (); ++ cfi_parse_separator (); ++ offset = cfi_parse_const (); ++ ++ if (arg == DW_CFA_def_cfa) ++ cfi_add_CFA_def_cfa (reg1, offset); ++ else ++ cfi_add_CFA_offset (reg1, offset); + break; + +- case CFA_register: +- if (cfi_parse_reg (¶m[0]) < 0) +- { +- as_bad (_("first argument to %s is not a register"), +- cfi_insn_str (arg)); +- return; +- } +- if (cfi_parse_reg (¶m[1]) < 0) +- { +- as_bad (_("second argument to %s is not a register"), +- cfi_insn_str (arg)); +- return; +- } ++ /* Instructions that take two arguments (register, register). */ ++ case DW_CFA_register: ++ reg1 = cfi_parse_reg (); ++ cfi_parse_separator (); ++ reg2 = cfi_parse_reg (); ++ ++ cfi_add_CFA_register (reg1, reg2); + break; + + /* Instructions that take one register argument. */ +- case CFA_def_cfa_register: +- if (cfi_parse_reg (¶m[0]) < 0) +- { +- as_bad (_("argument to %s is not a register"), cfi_insn_str (arg)); +- return; +- } ++ case DW_CFA_def_cfa_register: ++ reg1 = cfi_parse_reg (); ++ cfi_add_CFA_def_cfa_register (reg1); + break; + + /* Instructions that take one integer argument. */ +- case CFA_def_cfa_offset: +- if (cfi_parse_const (¶m[0]) < 0) +- { +- as_bad (_("argument to %s is not a number"), cfi_insn_str (arg)); +- return; +- } ++ case DW_CFA_def_cfa_offset: ++ offset = cfi_parse_const (); ++ cfi_add_CFA_def_cfa_offset (offset); + break; + + /* Special handling for pseudo-instruction. */ + case CFI_adjust_cfa_offset: +- if (cfi_parse_const (¶m[0]) < 0) +- { +- as_bad (_("argument to %s is not a number"), +- ".cfi_adjust_cfa_offset"); +- return; +- } +- param[0] += get_current_offset (cfi_info); +- arg = CFA_def_cfa_offset; ++ offset = cfi_parse_const (); ++ cfi_add_CFA_def_cfa_offset (cur_cfa_offset + offset); + break; + + default: +- as_bad (_("unknown CFI instruction %d (%s)"), arg, cfi_insn_str (arg)); +- return; ++ abort (); + } +- cfi_add_insn (arg, param[0], param[1]); ++ ++ demand_empty_rest_of_line (); + } + +-static symbolS * +-cfi_get_label (void) ++static void ++dot_cfi_startproc (int ignored ATTRIBUTE_UNUSED) + { +- char symname[40], *symbase=".Llbl_cfi"; +- symbolS *symbolP; +- unsigned int i = 0; ++ int simple = 0; + +- snprintf (symname, sizeof (symname), "%s_0x%lx", +- symbase, (long) frag_now_fix ()); +- while ((symbolP = symbol_find (symname))) ++ if (cur_fde_data) ++ { ++ as_bad (_("previous CFI entry not closed (missing .cfi_endproc)")); ++ return; ++ } ++ ++ cfi_new_fde (symbol_temp_new_now ()); ++ ++ SKIP_WHITESPACE (); ++ if (is_name_beginner (*input_line_pointer)) + { +- if ((S_GET_VALUE (symbolP) == frag_now_fix ()) +- && (S_GET_SEGMENT (symbolP) == now_seg)) +- return symbolP; ++ char *name, c; + +- snprintf (symname, sizeof (symname), "%s_0x%lx_%u", +- symbase, (long) frag_now_fix (), i++); ++ name = input_line_pointer; ++ c = get_symbol_end (); ++ ++ if (strcmp (name, "simple") == 0) ++ { ++ simple = 1; ++ *input_line_pointer = c; ++ } ++ else ++ input_line_pointer = name; + } +-#ifdef BFD_ASSEMBLER +- symbolP = (symbolS *) local_symbol_make (symname, now_seg, +- (valueT) frag_now_fix (), +- frag_now); +-#else +- symbolP = symbol_make (symname); +-#endif +- return symbolP; ++ demand_empty_rest_of_line (); ++ ++ if (!simple) ++ tc_cfi_frame_initial_instructions (); + } + + static void +-dot_cfi_startproc (void) ++dot_cfi_endproc (int ignored ATTRIBUTE_UNUSED) + { +-#ifdef tc_cfi_frame_initial_instructions +- const char *simple = "simple"; +-#endif +- +- if (cfi_info) ++ if (! cur_fde_data) + { +- as_bad (_("previous CFI entry not closed (missing .cfi_endproc)")); ++ as_bad (_(".cfi_endproc without corresponding .cfi_startproc")); + return; + } + +-#if defined(TARGET_USE_CFIPOP) +- /* Because this file is linked even for architectures that +- don't use CFI, we must wrap this call. */ +- if (current_config.addr_length == 0) +- tc_cfi_init (); +-#endif +- +- cfi_info = alloc_cfi_info (); ++ cfi_end_fde (symbol_temp_new_now ()); ++} + +- cfi_info->start_address = frag_now_fix (); +- cfi_info->last_address = cfi_info->start_address; +- cfi_info->labelname = S_GET_NAME (cfi_get_label ()); ++ ++/* Emit a single byte into the current segment. */ + +- SKIP_WHITESPACE (); +-#ifdef tc_cfi_frame_initial_instructions +- if (strncmp (simple, input_line_pointer, strlen (simple)) != 0) +- tc_cfi_frame_initial_instructions (); +- else +- input_line_pointer += strlen (simple); +-#endif ++static inline void ++out_one (int byte) ++{ ++ FRAG_APPEND_1_CHAR (byte); + } + +-#define cfi_is_advance_insn(insn) \ +- ((insn >= CFA_set_loc && insn <= CFA_advance_loc4) \ +- || insn == CFA_advance_loc) ++/* Emit a two-byte word into the current segment. */ + +-/* Output CFI instructions to the file. */ ++static inline void ++out_two (int data) ++{ ++ md_number_to_chars (frag_more (2), data, 2); ++} + +-enum data_types +- { +- t_ascii = 0, +- t_byte = 1, +- t_half = 2, +- t_long = 4, +- t_quad = 8, +- t_uleb128 = 0x10, +- t_sleb128 = 0x11 +- }; ++/* Emit a four byte word into the current segment. */ + +-static int +-output_data (char **p, unsigned long *size, enum data_types type, long value) ++static inline void ++out_four (int data) + { +- char *ptr = *p; +- unsigned int ret_size; +- +- switch (type) +- { +- case t_byte: +- ret_size = 1; +- break; +- case t_half: +- ret_size = 2; +- break; +- case t_long: +- ret_size = 4; +- break; +- case t_quad: +- case t_uleb128: +- case t_sleb128: +- ret_size = 8; +- break; +- default: +- /* This should never happen - throw an internal error. */ +- as_fatal (_("unknown type %d"), type); +- return 0; +- } +- +- if (*size < ret_size) +- { +- as_bad (_("output_data buffer is too small")); +- return 0; +- } +- +- switch (type) +- { +- case t_byte: +- *ptr = (char) value; +- if (verbose) +- printf ("\t.byte\t0x%x\n", (unsigned char) *ptr); +- break; +- case t_half: +- *(short *) ptr = (short) value & 0xFFFF; +- if (verbose) +- printf ("\t.half\t0x%x\n", (unsigned short) *ptr); +- break; +- case t_long: +- *(int *) ptr = (int) value & 0xFFFFFFFF; +- if (verbose) +- printf ("\t.long\t0x%x\n", (unsigned int) *ptr); +- break; +- case t_quad: +- *(long long *) ptr = (long long) value & 0xFFFFFFFF; +- if (verbose) +- printf ("\t.quad\t0x%x\n", (unsigned int) *ptr); +- break; +- case t_uleb128: +- case t_sleb128: +- ret_size = output_leb128 (ptr, value, type == t_sleb128); +- if (verbose) +- printf ("\t.%s\t0x%lx\n", +- type == t_sleb128 ? "sleb128" : "uleb128", +- value); +- break; +- default: +- as_fatal (_("unknown type %d"), type); +- return 0; +- } ++ md_number_to_chars (frag_more (4), data, 4); ++} + +- *size -= ret_size; +- *p += ret_size; ++/* Emit an unsigned "little-endian base 128" number. */ + +- return ret_size; ++static void ++out_uleb128 (addressT value) ++{ ++ output_leb128 (frag_more (sizeof_leb128 (value, 0)), value, 0); + } + +-static int +-cfi_output_insn (struct cfi_data *data, char **buf, unsigned long *buf_size) ++/* Emit an unsigned "little-endian base 128" number. */ ++ ++static void ++out_sleb128 (offsetT value) + { +- char **pbuf = buf, *orig_buf = *buf; +- unsigned long size; ++ output_leb128 (frag_more (sizeof_leb128 (value, 1)), value, 1); ++} + +- if (!data || !buf) +- as_fatal (_("cfi_output_insn called with NULL pointer")); ++static void ++output_cfi_insn (struct cfi_insn_data *insn) ++{ ++ offsetT offset; ++ unsigned int regno; + +- switch (data->insn) ++ switch (insn->insn) + { +- case CFA_advance_loc: +- if (verbose) +- printf ("\t# %s(%ld)\n", cfi_insn_str (data->insn), +- data->param[0]); +- if (data->param[0] <= 0x3F) +- { +- output_data (pbuf, buf_size, t_byte, CFA_advance_loc + +- (data->param[0] / current_config.code_align)); ++ case DW_CFA_advance_loc: ++ { ++ symbolS *from = insn->u.ll.lab1; ++ symbolS *to = insn->u.ll.lab2; ++ ++ if (symbol_get_frag (to) == symbol_get_frag (from)) ++ { ++ addressT delta = S_GET_VALUE (to) - S_GET_VALUE (from); ++ addressT scaled = delta / DWARF2_LINE_MIN_INSN_LENGTH; ++ ++ if (scaled <= 0x3F) ++ out_one (DW_CFA_advance_loc + scaled); ++ else if (delta <= 0xFF) ++ { ++ out_one (DW_CFA_advance_loc1); ++ out_one (delta); ++ } ++ else if (delta <= 0xFFFF) ++ { ++ out_one (DW_CFA_advance_loc2); ++ out_two (delta); ++ } ++ else ++ { ++ out_one (DW_CFA_advance_loc4); ++ out_four (delta); ++ } ++ } ++ else ++ { ++ expressionS exp; ++ ++ exp.X_op = O_subtract; ++ exp.X_add_symbol = to; ++ exp.X_op_symbol = from; ++ exp.X_add_number = 0; ++ ++ /* The code in ehopt.c expects that one byte of the encoding ++ is already allocated to the frag. This comes from the way ++ that it scans the .eh_frame section looking first for the ++ .byte DW_CFA_advance_loc4. */ ++ frag_more (1); ++ ++ frag_var (rs_cfa, 4, 0, DWARF2_LINE_MIN_INSN_LENGTH << 3, ++ make_expr_symbol (&exp), frag_now_fix () - 1, ++ (char *) frag_now); ++ } ++ } ++ break; ++ ++ case DW_CFA_def_cfa: ++ offset = insn->u.ri.offset; ++ if (offset < 0) ++ { ++ out_one (DW_CFA_def_cfa_sf); ++ out_uleb128 (insn->u.ri.reg); ++ out_uleb128 (offset); + } +- else if (data->param[0] <= 0xFF) ++ else + { +- output_data (pbuf, buf_size, t_byte, CFA_advance_loc1); +- output_data (pbuf, buf_size, t_byte, +- data->param[0] / current_config.code_align); ++ out_one (DW_CFA_def_cfa); ++ out_uleb128 (insn->u.ri.reg); ++ out_uleb128 (offset); + } +- else if (data->param[0] <= 0xFFFF) ++ break; ++ ++ case DW_CFA_def_cfa_register: ++ out_one (DW_CFA_def_cfa_register); ++ out_uleb128 (insn->u.i); ++ break; ++ ++ case DW_CFA_def_cfa_offset: ++ offset = insn->u.i; ++ if (offset < 0) + { +- output_data (pbuf, buf_size, t_byte, CFA_advance_loc2); +- output_data (pbuf, buf_size, t_half, +- data->param[0] / current_config.code_align); ++ out_one (DW_CFA_def_cfa_offset_sf); ++ out_sleb128 (offset); + } + else + { +- output_data (pbuf, buf_size, t_byte, CFA_advance_loc4); +- output_data (pbuf, buf_size, t_long, +- data->param[0] / current_config.code_align); ++ out_one (DW_CFA_def_cfa_offset); ++ out_uleb128 (offset); + } + break; + +- case CFA_def_cfa: +- if (verbose) +- printf ("\t# CFA_def_cfa(%ld,%ld)\n", +- data->param[0], data->param[1]); +- output_data (pbuf, buf_size, t_byte, CFA_def_cfa); +- output_data (pbuf, buf_size, t_uleb128, data->param[0]); +- output_data (pbuf, buf_size, t_uleb128, data->param[1]); +- break; +- +- case CFA_def_cfa_register: +- case CFA_def_cfa_offset: +- if (verbose) +- printf ("\t# %s(%ld)\n", cfi_insn_str (data->insn), +- data->param[0]); +- output_data (pbuf, buf_size, t_byte, data->insn); +- output_data (pbuf, buf_size, t_uleb128, data->param[0]); +- break; +- +- case CFA_offset: +- if (verbose) +- printf ("\t# %s(%ld,%ld)\n", cfi_insn_str (data->insn), +- data->param[0], data->param[1]); +- +- /* Check whether to use CFA_offset or CFA_offset_extended. */ +- if (data->param[0] <= 0x3F) +- output_data (pbuf, buf_size, t_byte, CFA_offset + data->param[0]); ++ case DW_CFA_offset: ++ regno = insn->u.ri.reg; ++ offset = insn->u.ri.offset / DWARF2_CIE_DATA_ALIGNMENT; ++ if (offset < 0) ++ { ++ out_one (DW_CFA_offset_extended); ++ out_uleb128 (regno); ++ out_sleb128 (offset); ++ } ++ else if (regno <= 0x3F) ++ { ++ out_one (DW_CFA_offset + regno); ++ out_uleb128 (offset); ++ } + else + { +- output_data (pbuf, buf_size, t_byte, CFA_offset_extended); +- output_data (pbuf, buf_size, t_uleb128, data->param[0]); ++ out_one (DW_CFA_offset_extended); ++ out_uleb128 (regno); ++ out_uleb128 (offset); + } +- output_data (pbuf, buf_size, t_uleb128, +- data->param[1] / current_config.data_align); + break; + +- case CFA_register: +- if (verbose) +- printf ("\t# %s(%ld,%ld)\n", cfi_insn_str (data->insn), +- data->param[0], data->param[1]); +- output_data (pbuf, buf_size, t_byte, CFA_register); +- output_data (pbuf, buf_size, t_uleb128, data->param[0]); +- output_data (pbuf, buf_size, t_uleb128, data->param[1]); +- break; +- +- case CFA_nop: +- if (verbose) +- printf ("\t# CFA_nop\n"); +- output_data (pbuf, buf_size, t_byte, CFA_nop); ++ case DW_CFA_register: ++ out_one (DW_CFA_register); ++ out_uleb128 (insn->u.rr.reg1); ++ out_uleb128 (insn->u.rr.reg2); ++ break; ++ ++ case DW_CFA_nop: ++ out_one (DW_CFA_nop); + break; + + default: +- as_warn ("CFA_unknown[%d](%ld,%ld)", data->insn, +- data->param[0], data->param[1]); ++ abort (); + } +- size = *pbuf - orig_buf; +- *buf = *pbuf; +- *buf_size -= size; +- return size; + } + + static void +-dot_cfi_endproc (void) ++output_cie (struct cie_entry *cie) + { +- struct cfi_data *data_ptr; +- struct cie_entry *cie_ptr; +- char *cie_buf, *fde_buf, *pbuf, *where; +- unsigned long buf_size, cie_size, fde_size, last_cie_offset; +- unsigned long fde_initloc_offset, fde_len_offset, fde_offset; +- segT saved_seg, cfi_seg; ++ symbolS *after_size_address, *end_address; + expressionS exp; ++ struct cfi_insn_data *i; + +- if (! cfi_info) +- { +- as_bad (_(".cfi_endproc without corresponding .cfi_startproc")); +- return; +- } +- cfi_info->end_address = frag_now_fix (); +- +- /* Open .eh_frame section. */ +- saved_seg = now_seg; +- cfi_seg = subseg_new (".eh_frame", 0); +-#ifdef BFD_ASSEMBLER +- bfd_set_section_flags (stdoutput, cfi_seg, +- SEC_ALLOC | SEC_LOAD | SEC_RELOC | SEC_DATA); +-#endif +- subseg_set (cfi_seg, 0); ++ cie->start_address = symbol_temp_new_now (); ++ after_size_address = symbol_temp_make (); ++ end_address = symbol_temp_make (); ++ ++ exp.X_op = O_subtract; ++ exp.X_add_symbol = end_address; ++ exp.X_op_symbol = after_size_address; ++ exp.X_add_number = 0; ++ ++ emit_expr (&exp, 4); /* Length */ ++ symbol_set_value_now (after_size_address); ++ out_four (0); /* CIE id */ ++ out_one (DW_CIE_VERSION); /* Version */ ++ out_one ('z'); /* Augmentation */ ++ out_one ('R'); ++ out_one (0); ++ out_uleb128 (DWARF2_LINE_MIN_INSN_LENGTH); /* Code alignment */ ++ out_sleb128 (DWARF2_CIE_DATA_ALIGNMENT); /* Data alignment */ ++ out_one (cie->return_column); /* Return column */ ++ out_uleb128 (1); /* Augmentation size */ ++ out_one (DW_EH_PE_pcrel | DW_EH_PE_sdata4); ++ ++ if (cie->first) ++ for (i = cie->first; i != cie->last; i = i->next) ++ output_cfi_insn (i); + +- /* Build CIE. */ +- cie_buf = xcalloc (1024, 1); +- /* Skip space for CIE length. */ +- pbuf = cie_buf + 4; +- buf_size = 1020; +- +- if (verbose) +- printf ("# CIE *****\n"); +- +- /* CIE id. */ +- output_data (&pbuf, &buf_size, t_long, 0x0); +- /* Version. */ +- output_data (&pbuf, &buf_size, t_byte, 1); +- /* Augmentation. */ +- output_data (&pbuf, &buf_size, t_byte, 0); +- /* Code alignment. */ +- output_data (&pbuf, &buf_size, t_uleb128, current_config.code_align); +- /* Data alignment. */ +- output_data (&pbuf, &buf_size, t_sleb128, current_config.data_align); +- /* Return address column. */ +- output_data (&pbuf, &buf_size, t_byte, current_config.ra_column); +- +- /* Build CFI instructions. */ +- data_ptr = cfi_info->data; +- while (data_ptr && !cfi_is_advance_insn (data_ptr->insn)) +- { +- cfi_output_insn (data_ptr, &pbuf, &buf_size); +- data_ptr = data_ptr->next; +- } +- +- /* Align the whole data to current_config.eh_align. */ +- cie_size = pbuf - cie_buf; +- cie_size += current_config.eh_align - cie_size % current_config.eh_align; +- +- /* CIE length. */ +- pbuf = cie_buf; +- output_data (&pbuf, &buf_size, t_long, cie_size - 4); +- +- /* OK, we built the CIE. Let's write it to the file... */ +- last_cie_offset = frag_now_fix (); +- +- /* Check if we have already emitted the exactly same CIE. +- If yes then use its offset instead and don't put out +- the new one. */ +- cie_ptr = cie_root; +- while (cie_ptr) +- { +- if (cie_ptr->size == cie_size - 4 +- && memcmp (cie_ptr->data, cie_buf + 4, cie_ptr->size) == 0) +- break; +- cie_ptr = cie_ptr->next; +- } +- +- /* If we have found the same CIE, use it... */ +- if (cie_ptr) +- { +- if (verbose) +- printf ("# Duplicate CIE found. Previous is at offset %lu\n", +- cie_ptr->offset); +- last_cie_offset = cie_ptr->offset; +- } +- else +- { +- /* Otherwise join this CIE to the list. */ +- where = (unsigned char *) frag_more (cie_size); +- memcpy (where, cie_buf, cie_size); +- if (cie_root) +- { +- cie_ptr = cie_root; +- while (cie_ptr->next) +- cie_ptr = cie_ptr->next; +- cie_ptr->next = calloc (sizeof (struct cie_entry), 1); +- cie_ptr = cie_ptr->next; +- } +- else +- { +- cie_root = calloc (sizeof (struct cie_entry), 1); +- cie_ptr = cie_root; +- } ++ frag_align (2, 0, 0); ++ symbol_set_value_now (end_address); ++} + +- cie_ptr->size = cie_size - 4; +- cie_ptr->data = calloc (cie_ptr->size, 1); +- cie_ptr->offset = last_cie_offset; +- memcpy (cie_ptr->data, cie_buf + 4, cie_ptr->size); +- } ++static void ++output_fde (struct fde_entry *fde, struct cie_entry *cie, ++ struct cfi_insn_data *first) ++{ ++ symbolS *after_size_address, *end_address; ++ expressionS exp; + +- /* Clean up. */ +- free (cie_buf); ++ after_size_address = symbol_temp_make (); ++ end_address = symbol_temp_make (); + +- /* Build the FDE... */ +- fde_buf = xcalloc (1024, 1); +- pbuf = fde_buf; +- buf_size = 1024; ++ exp.X_op = O_subtract; ++ exp.X_add_symbol = end_address; ++ exp.X_op_symbol = after_size_address; ++ exp.X_add_number = 0; ++ emit_expr (&exp, 4); /* Length */ ++ symbol_set_value_now (after_size_address); + +- /* Offset of this FDE in current fragment. */ +- fde_offset = frag_now_fix (); ++ exp.X_add_symbol = after_size_address; ++ exp.X_op_symbol = cie->start_address; ++ emit_expr (&exp, 4); /* CIE offset */ ++ ++ exp.X_add_symbol = fde->start_address; ++ exp.X_op_symbol = symbol_temp_new_now (); ++ emit_expr (&exp, 4); /* Code offset */ + +- if (verbose) +- { +- printf ("# FDE: start=0x%lx, end=0x%lx, delta=%d\n", +- (long) cfi_info->start_address, +- (long) cfi_info->end_address, +- (int) (cfi_info->end_address - cfi_info->start_address)); +- } ++ exp.X_add_symbol = fde->end_address; ++ exp.X_op_symbol = fde->start_address; /* Code length */ ++ emit_expr (&exp, 4); + +- /* FDE length (t_long, 4 bytes) - will be set later. */ +- fde_len_offset = pbuf - fde_buf; +- pbuf += 4; +- buf_size -= 4; ++ out_uleb128 (0); /* Augmentation size */ + +- /* CIE pointer - offset from here. */ +- output_data (&pbuf, &buf_size, t_long, fde_offset - last_cie_offset + 4); ++ for (; first; first = first->next) ++ output_cfi_insn (first); + +- /* FDE initial location - this must be set relocatable! */ +- fde_initloc_offset = pbuf - fde_buf + fde_offset; +- output_data (&pbuf, &buf_size, current_config.addr_length, +- cfi_info->start_address); ++ frag_align (2, 0, 0); ++ symbol_set_value_now (end_address); ++} + +- /* FDE address range. */ +- output_data (&pbuf, &buf_size, current_config.addr_length, +- cfi_info->end_address - cfi_info->start_address); ++static struct cie_entry * ++select_cie_for_fde (struct fde_entry *fde, struct cfi_insn_data **pfirst) ++{ ++ struct cfi_insn_data *i, *j; ++ struct cie_entry *cie; + +- while (data_ptr) ++ for (cie = cie_root; cie; cie = cie->next) + { +- cfi_output_insn (data_ptr, &pbuf, &buf_size); +- data_ptr = data_ptr->next; +- } ++ if (cie->return_column != fde->return_column) ++ continue; ++ for (i = cie->first, j = fde->data; ++ i != cie->last && j != NULL; ++ i = i->next, j = j->next) ++ { ++ if (i->insn != j->insn) ++ goto fail; ++ switch (i->insn) ++ { ++ case DW_CFA_advance_loc: ++ /* We reached the first advance in the FDE, but did not ++ reach the end of the CIE list. */ ++ goto fail; + +- fde_size = pbuf - fde_buf; +- fde_size += current_config.eh_align - fde_size % current_config.eh_align; ++ case DW_CFA_offset: ++ case DW_CFA_def_cfa: ++ if (i->u.ri.reg != j->u.ri.reg) ++ goto fail; ++ if (i->u.ri.offset != j->u.ri.offset) ++ goto fail; ++ break; + +- /* Now we can set FDE length. */ +- pbuf = fde_buf + fde_len_offset; +- buf_size = 4; +- output_data (&pbuf, &buf_size, t_long, fde_size - 4); ++ case DW_CFA_register: ++ if (i->u.rr.reg1 != j->u.rr.reg1) ++ goto fail; ++ if (i->u.rr.reg2 != j->u.rr.reg2) ++ goto fail; ++ break; + +- /* Copy FDE to objfile. */ +- where = (unsigned char *) frag_more (fde_size); +- memcpy (where, fde_buf, fde_size); ++ case DW_CFA_def_cfa_register: ++ if (i->u.r != j->u.r) ++ goto fail; ++ break; + +- /* Set relocation for initial address. */ +- buf_size = current_config.addr_length; +- memset (&exp, 0, sizeof (exp)); +- exp.X_op = O_symbol; +- exp.X_add_symbol = symbol_find (cfi_info->labelname); +- fix_new_exp (frag_now, fde_initloc_offset, +- current_config.addr_length, +- &exp, 0, current_config.reloc_type); ++ case DW_CFA_def_cfa_offset: ++ if (i->u.i != j->u.i) ++ goto fail; ++ break; + +- /* Clean up. */ +- free (fde_buf); ++ default: ++ abort (); ++ } ++ } + +- free (cfi_info); +- cfi_info = NULL; ++ /* Success if we reached the end of the CIE list, and we've either ++ run out of FDE entries or we've encountered an advance. */ ++ if (i == cie->last && (!j || j->insn == DW_CFA_advance_loc)) ++ { ++ *pfirst = j; ++ return cie; ++ } + +- /* Restore previous segment. */ +- subseg_set (saved_seg, 0); +-} ++ fail:; ++ } + +-void +-dot_cfi (int arg) +-{ +- long param; ++ cie = xmalloc (sizeof (struct cie_entry)); ++ cie->next = cie_root; ++ cie_root = cie; ++ cie->return_column = fde->return_column; ++ cie->first = fde->data; + +- switch (arg) +- { +- case CFI_startproc: +- dot_cfi_startproc (); +- break; +- case CFI_endproc: +- dot_cfi_endproc (); +- break; +- case CFA_def_cfa: +- case CFA_def_cfa_register: +- case CFA_def_cfa_offset: +- case CFA_offset: +- case CFA_register: +- case CFI_adjust_cfa_offset: +- cfi_make_insn (arg); +- break; +- case CFI_verbose: +- if (cfi_parse_const (¶m) >= 0) +- verbose = (int) param; +- else +- verbose = 1; +- break; +- default: +- as_bad (_("unknown CFI code 0x%x (%s)"), arg, cfi_insn_str (arg)); ++ for (i = cie->first; i ; i = i->next) ++ if (i->insn == DW_CFA_advance_loc) + break; +- } +- ignore_rest_of_line (); +-} + +-void +-cfi_set_config (struct cfi_config *cfg) +-{ +- assert (cfg != NULL); +- assert (cfg->addr_length > 0); ++ cie->last = i; ++ *pfirst = i; ++ ++ output_cie (cie); + +- current_config = *cfg; ++ return cie; + } + + void + cfi_finish (void) + { +- if (cfi_info) +- as_bad (_("open CFI at the end of file; missing .cfi_endproc directive")); ++ segT cfi_seg; ++ struct fde_entry *fde; ++ int save_flag_traditional_format; ++ ++ if (cur_fde_data) ++ { ++ as_bad (_("open CFI at the end of file; missing .cfi_endproc directive")); ++ cur_fde_data->end_address = cur_fde_data->start_address; ++ } ++ ++ if (all_fde_data == 0) ++ return; ++ ++ /* Open .eh_frame section. */ ++ cfi_seg = subseg_new (".eh_frame", 0); ++#ifdef BFD_ASSEMBLER ++ bfd_set_section_flags (stdoutput, cfi_seg, ++ SEC_ALLOC | SEC_LOAD | SEC_RELOC | SEC_DATA); ++#endif ++ subseg_set (cfi_seg, 0); ++ record_alignment (cfi_seg, 2); ++ ++ /* Make sure check_eh_frame doesn't do anything with our output. */ ++ save_flag_traditional_format = flag_traditional_format; ++ flag_traditional_format = 1; ++ ++ for (fde = all_fde_data; fde ; fde = fde->next) ++ { ++ struct cfi_insn_data *first; ++ struct cie_entry *cie; ++ ++ cie = select_cie_for_fde (fde, &first); ++ output_fde (fde, cie, first); ++ } ++ ++ flag_traditional_format = save_flag_traditional_format; + } +--- gas/dw2gencfi.h 20 May 2003 07:58:06 -0000 1.1 ++++ gas/dw2gencfi.h 27 May 2003 16:52:46 -0000 1.2 +@@ -24,77 +24,23 @@ + + #include "elf/dwarf2.h" + +-struct cfi_config { +- /* Target address length in bytes. (usually 4 or 8). +- Round it up for archs like S/390 with 31b addresses. */ +- unsigned int addr_length; +- +- /* Alignment of .eh_frame blocks in bytes (usually 1, 4 or 8). */ +- unsigned int eh_align; +- +- /* Code alignment (1 for x86/amd64 machines, 4 or 8 for +- RISC machines). Consult Dwarf2 standard for details. */ +- int code_align; +- +- /* Data (stack) alignment (-4 on x86, -8 on amd64, something +- positive on archs where stack grows up). Consult Dwarf2 +- standard for details. */ +- int data_align; +- +- /* Return address column (0x8 on x86, 0x10 on amd64). Consult +- Dwarf2 standard for details. */ +- int ra_column; +- +- /* Relocation type for init_addr FDE record. (BFD_RELOC_64 +- on amd64). */ +- int reloc_type; +-}; +- +-/* Codes of CFI instructions taken from Dwarf2 standard. */ +-enum cfi_insn { +- CFA_nop = DW_CFA_nop, +- CFA_set_loc = DW_CFA_set_loc, +- CFA_advance_loc1 = DW_CFA_advance_loc1, +- CFA_advance_loc2 = DW_CFA_advance_loc2, +- CFA_advance_loc4 = DW_CFA_advance_loc4, +- CFA_offset_extended = DW_CFA_offset_extended, +- CFA_resotre_extended = DW_CFA_restore_extended, +- CFA_undefined = DW_CFA_undefined, +- CFA_same_value = DW_CFA_same_value, +- CFA_register = DW_CFA_register, +- CFA_remember_state = DW_CFA_remember_state, +- CFA_restore_state = DW_CFA_restore_state, +- CFA_def_cfa = DW_CFA_def_cfa, +- CFA_def_cfa_register = DW_CFA_def_cfa_register, +- CFA_def_cfa_offset = DW_CFA_def_cfa_offset, +- CFA_advance_loc = DW_CFA_advance_loc, +- CFA_offset = DW_CFA_offset, +- CFA_restore = DW_CFA_restore, +- +- /* These don't belong to the standard. */ +- CFI_startproc = 0xff00, +- CFI_endproc = 0xff01, +- CFI_adjust_cfa_offset = 0xff10, +- CFI_verbose = 0xffff +-}; ++struct symbol; + + extern const pseudo_typeS cfi_pseudo_table[]; + +-/* Insert .cfi_* directives to the list of pseudo-ops. */ +-void cfi_pop_insert PARAMS ((void)); +- +-/* Set/change setup of the CFI machinery. This change won't +- affect already generated CIEs/FDEs. */ +-void cfi_set_config PARAMS ((struct cfi_config *cfg)); +- + /* cfi_finish() is called at the end of file. It will complain if + the last CFI wasn't properly closed by .cfi_endproc. */ +-void cfi_finish PARAMS ((void)); ++extern void cfi_finish (void); + +-/* Add CFI instruction to the list of instructions +- of the current frame. cfi_add_insn() could be used +- in tc_cfi_frame_initial_instructions() to add instructions +- needed for every frame (ie. those that usually go to CIE). */ +-void cfi_add_insn (enum cfi_insn insn, long param0, long param1); ++/* Entry points for backends to add unwind information. */ ++extern void cfi_new_fde (struct symbol *); ++extern void cfi_end_fde (struct symbol *); ++extern void cfi_set_return_column (unsigned); ++extern void cfi_add_advance_loc (struct symbol *); ++extern void cfi_add_CFA_offset (unsigned, offsetT); ++extern void cfi_add_CFA_def_cfa (unsigned, offsetT); ++extern void cfi_add_CFA_register (unsigned, unsigned); ++extern void cfi_add_CFA_def_cfa_register (unsigned); ++extern void cfi_add_CFA_def_cfa_offset (offsetT); + + #endif /* DW2GENCFI_H */ +--- gas/dwarf2dbg.c 21 Apr 2003 18:23:25 -0000 1.62 ++++ gas/dwarf2dbg.c 27 May 2003 16:00:04 -0000 1.63 +@@ -157,9 +157,6 @@ static bfd_boolean loc_directive_seen; + /* Current location as indicated by the most recent .loc directive. */ + static struct dwarf2_line_info current; + +-/* Fake label name. */ +-static char const fake_label_name[] = ".L0\001"; +- + /* The size of an address on the target. */ + static unsigned int sizeof_address; + +@@ -174,8 +171,6 @@ static void out_two PARAMS ((int)); + static void out_four PARAMS ((int)); + static void out_abbrev PARAMS ((int, int)); + static void out_uleb128 PARAMS ((addressT)); +-static symbolS *symbol_new_now PARAMS ((void)); +-static void set_symbol_value_now PARAMS ((symbolS *)); + static offsetT get_frag_fix PARAMS ((fragS *)); + static void out_set_addr PARAMS ((segT, fragS *, addressT)); + static int size_inc_line_addr PARAMS ((int, addressT)); +@@ -621,25 +616,6 @@ out_abbrev (name, form) + out_uleb128 (form); + } + +-/* Create a new fake symbol whose value is the current position. */ +- +-static symbolS * +-symbol_new_now () +-{ +- return symbol_new (fake_label_name, now_seg, frag_now_fix (), frag_now); +-} +- +-/* Set the value of SYM to the current position in the current segment. */ +- +-static void +-set_symbol_value_now (sym) +- symbolS *sym; +-{ +- S_SET_SEGMENT (sym, now_seg); +- S_SET_VALUE (sym, frag_now_fix ()); +- symbol_set_frag (sym, frag_now); +-} +- + /* Get the size of a fragment. */ + + static offsetT +@@ -676,7 +652,7 @@ out_set_addr (seg, frag, ofs) + expressionS expr; + symbolS *sym; + +- sym = symbol_new (fake_label_name, seg, ofs, frag); ++ sym = symbol_temp_new (seg, ofs, frag); + + out_opcode (DW_LNS_extended_op); + out_uleb128 (sizeof_address + 1); +@@ -894,8 +870,8 @@ relax_inc_line_addr (line_delta, seg, to + expressionS expr; + int max_chars; + +- to_sym = symbol_new (fake_label_name, seg, to_ofs, to_frag); +- from_sym = symbol_new (fake_label_name, seg, from_ofs, from_frag); ++ to_sym = symbol_temp_new (seg, to_ofs, to_frag); ++ from_sym = symbol_temp_new (seg, from_ofs, from_frag); + + expr.X_op = O_subtract; + expr.X_add_symbol = to_sym; +@@ -1124,9 +1100,9 @@ out_debug_line (line_seg) + + subseg_set (line_seg, 0); + +- line_start = symbol_new_now (); +- prologue_end = symbol_make (fake_label_name); +- line_end = symbol_make (fake_label_name); ++ line_start = symbol_temp_new_now (); ++ prologue_end = symbol_temp_make (); ++ line_end = symbol_temp_make (); + + /* Total length of the information for this compilation unit. */ + expr.X_op = O_subtract; +@@ -1188,13 +1164,13 @@ out_debug_line (line_seg) + + out_file_list (); + +- set_symbol_value_now (prologue_end); ++ symbol_set_value_now (prologue_end); + + /* For each section, emit a statement program. */ + for (s = all_segs; s; s = s->next) + process_entries (s->seg, s->head->head); + +- set_symbol_value_now (line_end); ++ symbol_set_value_now (line_end); + } + + /* Emit data for .debug_aranges. */ +@@ -1250,11 +1226,11 @@ out_debug_aranges (aranges_seg, info_seg + symbolS *beg, *end; + + frag = first_frag_for_seg (s->seg); +- beg = symbol_new (fake_label_name, s->seg, 0, frag); ++ beg = symbol_temp_new (s->seg, 0, frag); + s->text_start = beg; + + frag = last_frag_for_seg (s->seg); +- end = symbol_new (fake_label_name, s->seg, get_frag_fix (frag), frag); ++ end = symbol_temp_new (s->seg, get_frag_fix (frag), frag); + s->text_end = end; + + expr.X_op = O_symbol; +@@ -1322,8 +1298,8 @@ out_debug_info (info_seg, abbrev_seg, li + + subseg_set (info_seg, 0); + +- info_start = symbol_new_now (); +- info_end = symbol_make (fake_label_name); ++ info_start = symbol_temp_new_now (); ++ info_end = symbol_temp_make (); + + /* Compilation Unit length. */ + expr.X_op = O_subtract; +@@ -1421,7 +1397,7 @@ out_debug_info (info_seg, abbrev_seg, li + dwarf2 draft has no standard code for assembler. */ + out_two (DW_LANG_Mips_Assembler); + +- set_symbol_value_now (info_end); ++ symbol_set_value_now (info_end); + } + + void +--- gas/expr.c 18 Oct 2002 01:56:39 -0000 1.46 ++++ gas/expr.c 27 May 2003 19:19:29 -0000 1.47 +@@ -67,7 +67,6 @@ make_expr_symbol (expressionP) + expressionS *expressionP; + { + expressionS zero; +- const char *fake; + symbolS *symbolP; + struct expr_symbol_line *n; + +@@ -91,13 +90,11 @@ make_expr_symbol (expressionP) + expressionP = &zero; + } + +- fake = FAKE_LABEL_NAME; +- + /* Putting constant symbols in absolute_section rather than + expr_section is convenient for the old a.out code, for which + S_GET_SEGMENT does not always retrieve the value put in by + S_SET_SEGMENT. */ +- symbolP = symbol_create (fake, ++ symbolP = symbol_create (FAKE_LABEL_NAME, + (expressionP->X_op == O_constant + ? absolute_section + : expr_section), +@@ -745,13 +742,8 @@ current_location (expressionp) + } + else + { +- symbolS *symbolp; +- +- symbolp = symbol_new (FAKE_LABEL_NAME, now_seg, +- (valueT) frag_now_fix (), +- frag_now); + expressionp->X_op = O_symbol; +- expressionp->X_add_symbol = symbolp; ++ expressionp->X_add_symbol = symbol_temp_new_now (); + expressionp->X_add_number = 0; + } + } +--- gas/macro.c 13 Mar 2003 11:49:33 -0000 1.21 ++++ gas/macro.c 2 Jun 2003 15:03:20 -0000 1.22 +@@ -637,6 +637,7 @@ sub_actual (start, in, t, formal_hash, k + { + /* Doing this permits people to use & in macro bodies. */ + sb_add_char (out, '&'); ++ sb_add_sb (out, t); + } + else if (copyifnotthere) + { +--- gas/read.c 20 May 2003 07:58:06 -0000 1.62 ++++ gas/read.c 2 Jun 2003 22:48:58 -0000 1.63 +@@ -3444,6 +3444,8 @@ emit_expr (exp, nbytes) + if (need_pass_2) + return; + ++ dot_value = frag_now_fix (); ++ + #ifndef NO_LISTING + #ifdef OBJ_ELF + /* When gcc emits DWARF 1 debugging pseudo-ops, a line number will +--- gas/stabs.c 18 May 2002 12:53:30 -0000 1.19 ++++ gas/stabs.c 27 May 2003 19:19:29 -0000 1.20 +@@ -371,13 +371,11 @@ s_stab_generic (what, stab_secname, stab + } + else + { +- const char *fake; + symbolS *symbol; + expressionS exp; + + /* Arrange for a value representing the current location. */ +- fake = FAKE_LABEL_NAME; +- symbol = symbol_new (fake, saved_seg, dot, saved_frag); ++ symbol = symbol_temp_new (saved_seg, dot, saved_frag); + + exp.X_op = O_symbol; + exp.X_add_symbol = symbol; +--- gas/symbols.c 20 May 2003 07:58:06 -0000 1.44 ++++ gas/symbols.c 27 May 2003 19:19:29 -0000 1.46 +@@ -588,6 +588,27 @@ symbol_make (name) + return (symbolP); + } + ++symbolS * ++symbol_temp_new (seg, ofs, frag) ++ segT seg; ++ valueT ofs; ++ fragS *frag; ++{ ++ return symbol_new (FAKE_LABEL_NAME, seg, ofs, frag); ++} ++ ++symbolS * ++symbol_temp_new_now () ++{ ++ return symbol_temp_new (now_seg, frag_now_fix (), frag_now); ++} ++ ++symbolS * ++symbol_temp_make () ++{ ++ return symbol_make (FAKE_LABEL_NAME); ++} ++ + /* Implement symbol table lookup. + In: A symbol's name as a string: '\0' can't be part of a symbol name. + Out: NULL if the name was not in the symbol table, else the address +@@ -2059,6 +2080,17 @@ symbol_set_value_expression (s, exp) + if (LOCAL_SYMBOL_CHECK (s)) + s = local_symbol_convert ((struct local_symbol *) s); + s->sy_value = *exp; ++} ++ ++/* Set the value of SYM to the current position in the current segment. */ ++ ++void ++symbol_set_value_now (sym) ++ symbolS *sym; ++{ ++ S_SET_SEGMENT (sym, now_seg); ++ S_SET_VALUE (sym, frag_now_fix ()); ++ symbol_set_frag (sym, frag_now); + } + + /* Set the frag of a symbol. */ +--- gas/symbols.h 20 May 2003 07:58:06 -0000 1.12 ++++ gas/symbols.h 27 May 2003 16:00:04 -0000 1.13 +@@ -59,6 +59,10 @@ symbolS *symbol_create PARAMS ((const ch + fragS * frag)); + struct local_symbol *local_symbol_make PARAMS ((const char *name, segT section, + valueT value, fragS * frag)); ++symbolS *symbol_temp_new PARAMS ((segT, valueT, fragS *)); ++symbolS *symbol_temp_new_now PARAMS ((void)); ++symbolS *symbol_temp_make PARAMS ((void)); ++ + symbolS *colon PARAMS ((const char *sym_name)); + void local_colon PARAMS ((int n)); + void symbol_begin PARAMS ((void)); +@@ -172,6 +176,7 @@ extern symbolS *symbol_next PARAMS ((sym + extern expressionS *symbol_get_value_expression PARAMS ((symbolS *)); + extern void symbol_set_value_expression PARAMS ((symbolS *, + const expressionS *)); ++extern void symbol_set_value_now PARAMS ((symbolS *)); + extern void symbol_set_frag PARAMS ((symbolS *, fragS *)); + extern fragS *symbol_get_frag PARAMS ((symbolS *)); + extern void symbol_mark_used PARAMS ((symbolS *)); +--- gas/config/tc-alpha.c 3 May 2003 16:04:11 -0000 1.56 ++++ gas/config/tc-alpha.c 30 May 2003 03:01:11 -0000 1.57 +@@ -60,6 +60,7 @@ + #ifdef OBJ_ELF + #include "elf/alpha.h" + #include "dwarf2dbg.h" ++#include "dw2gencfi.h" + #endif + + #include "safe-ctype.h" +@@ -407,11 +408,6 @@ static symbolS *alpha_lit8_symbol; + static offsetT alpha_lit8_literal; + #endif + +-#ifdef OBJ_ELF +-/* The active .ent symbol. */ +-static symbolS *alpha_cur_ent_sym; +-#endif +- + /* Is the assembler not allowed to use $at? */ + static int alpha_noat_on = 0; + +@@ -4382,6 +4378,25 @@ s_alpha_sdata (ignore) + #endif + + #ifdef OBJ_ELF ++struct alpha_elf_frame_data ++{ ++ symbolS *func_sym; ++ symbolS *func_end_sym; ++ symbolS *prologue_sym; ++ unsigned int mask; ++ unsigned int fmask; ++ int fp_regno; ++ int ra_regno; ++ offsetT frame_size; ++ offsetT mask_offset; ++ offsetT fmask_offset; ++ ++ struct alpha_elf_frame_data *next; ++}; ++ ++static struct alpha_elf_frame_data *all_frame_data; ++static struct alpha_elf_frame_data **plast_frame_data = &all_frame_data; ++static struct alpha_elf_frame_data *cur_frame_data; + + /* Handle the .section pseudo-op. This is like the usual one, but it + clears alpha_insn_label and restores auto alignment. */ +@@ -4418,12 +4433,21 @@ s_alpha_ent (dummy) + { + symbolS *sym; + +- if (alpha_cur_ent_sym) ++ if (cur_frame_data) + as_warn (_("nested .ent directives")); + + sym = symbol_find_or_make (name); + symbol_get_bfdsym (sym)->flags |= BSF_FUNCTION; +- alpha_cur_ent_sym = sym; ++ ++ cur_frame_data = calloc (1, sizeof (*cur_frame_data)); ++ cur_frame_data->func_sym = sym; ++ ++ /* Provide sensible defaults. */ ++ cur_frame_data->fp_regno = 30; /* sp */ ++ cur_frame_data->ra_regno = 26; /* ra */ ++ ++ *plast_frame_data = cur_frame_data; ++ plast_frame_data = &cur_frame_data->next; + + /* The .ent directive is sometimes followed by a number. Not sure + what it really means, but ignore it. */ +@@ -4463,22 +4487,27 @@ s_alpha_end (dummy) + symbolS *sym; + + sym = symbol_find (name); +- if (sym != alpha_cur_ent_sym) ++ if (!cur_frame_data) ++ as_warn (_(".end directive without matching .ent")); ++ else if (sym != cur_frame_data->func_sym) + as_warn (_(".end directive names different symbol than .ent")); + + /* Create an expression to calculate the size of the function. */ + if (sym) + { +- symbol_get_obj (sym)->size = +- (expressionS *) xmalloc (sizeof (expressionS)); +- symbol_get_obj (sym)->size->X_op = O_subtract; +- symbol_get_obj (sym)->size->X_add_symbol +- = symbol_new ("L0\001", now_seg, frag_now_fix (), frag_now); +- symbol_get_obj (sym)->size->X_op_symbol = sym; +- symbol_get_obj (sym)->size->X_add_number = 0; ++ OBJ_SYMFIELD_TYPE *obj = symbol_get_obj (sym); ++ expressionS *exp = xmalloc (sizeof (expressionS)); ++ ++ obj->size = exp; ++ exp->X_op = O_subtract; ++ exp->X_add_symbol = symbol_temp_new_now (); ++ exp->X_op_symbol = sym; ++ exp->X_add_number = 0; ++ ++ cur_frame_data->func_end_sym = exp->X_add_symbol; + } + +- alpha_cur_ent_sym = NULL; ++ cur_frame_data = NULL; + + *input_line_pointer = name_end; + } +@@ -4498,7 +4527,45 @@ s_alpha_mask (fp) + ecoff_directive_mask (0); + } + else +- discard_rest_of_line (); ++ { ++ long val; ++ offsetT offset; ++ ++ if (!cur_frame_data) ++ { ++ if (fp) ++ as_warn (_(".fmask outside of .ent")); ++ else ++ as_warn (_(".mask outside of .ent")); ++ discard_rest_of_line (); ++ return; ++ } ++ ++ if (get_absolute_expression_and_terminator (&val) != ',') ++ { ++ if (fp) ++ as_warn (_("bad .fmask directive")); ++ else ++ as_warn (_("bad .mask directive")); ++ --input_line_pointer; ++ discard_rest_of_line (); ++ return; ++ } ++ ++ offset = get_absolute_expression (); ++ demand_empty_rest_of_line (); ++ ++ if (fp) ++ { ++ cur_frame_data->fmask = val; ++ cur_frame_data->fmask_offset = offset; ++ } ++ else ++ { ++ cur_frame_data->mask = val; ++ cur_frame_data->mask_offset = offset; ++ } ++ } + } + + static void +@@ -4508,7 +4575,36 @@ s_alpha_frame (dummy) + if (ECOFF_DEBUGGING) + ecoff_directive_frame (0); + else +- discard_rest_of_line (); ++ { ++ long val; ++ ++ if (!cur_frame_data) ++ { ++ as_warn (_(".frame outside of .ent")); ++ discard_rest_of_line (); ++ return; ++ } ++ ++ cur_frame_data->fp_regno = tc_get_register (1); ++ ++ SKIP_WHITESPACE (); ++ if (*input_line_pointer++ != ',' ++ || get_absolute_expression_and_terminator (&val) != ',') ++ { ++ as_warn (_("bad .frame directive")); ++ --input_line_pointer; ++ discard_rest_of_line (); ++ return; ++ } ++ cur_frame_data->frame_size = val; ++ ++ cur_frame_data->ra_regno = tc_get_register (0); ++ ++ /* Next comes the "offset of saved $a0 from $sp". In gcc terms ++ this is current_function_pretend_args_size. There's no place ++ to put this value, so ignore it. */ ++ s_ignore (42); ++ } + } + + static void +@@ -4524,7 +4620,7 @@ s_alpha_prologue (ignore) + if (ECOFF_DEBUGGING) + sym = ecoff_get_cur_proc_sym (); + else +- sym = alpha_cur_ent_sym; ++ sym = cur_frame_data ? cur_frame_data->func_sym : NULL; + + if (sym == NULL) + { +@@ -4549,6 +4645,9 @@ s_alpha_prologue (ignore) + as_bad (_("Invalid argument %d to .prologue."), arg); + break; + } ++ ++ if (cur_frame_data) ++ cur_frame_data->prologue_sym = symbol_temp_new_now (); + } + + static char *first_file_directive; +@@ -4641,6 +4740,87 @@ s_alpha_coff_wrapper (which) + as_bad (_("ECOFF debugging is disabled.")); + ignore_rest_of_line (); + } ++} ++ ++/* Called at the end of assembly. Here we emit unwind info for frames ++ unless the compiler has done it for us. */ ++ ++void ++alpha_elf_md_end (void) ++{ ++ struct alpha_elf_frame_data *p; ++ ++ if (cur_frame_data) ++ as_warn (_(".ent directive without matching .end")); ++ ++ /* If someone has generated the unwind info themselves, great. */ ++ if (bfd_get_section_by_name (stdoutput, ".eh_frame") != NULL) ++ return; ++ ++ /* Generate .eh_frame data for the unwind directives specified. */ ++ for (p = all_frame_data; p ; p = p->next) ++ if (p->prologue_sym) ++ { ++ /* Create a temporary symbol at the same location as our ++ function symbol. This prevents problems with globals. */ ++ cfi_new_fde (symbol_temp_new (S_GET_SEGMENT (p->func_sym), ++ S_GET_VALUE (p->func_sym), ++ symbol_get_frag (p->func_sym))); ++ ++ cfi_set_return_column (p->ra_regno); ++ cfi_add_CFA_def_cfa_register (30); ++ if (p->fp_regno != 30 || p->mask || p->fmask || p->frame_size) ++ { ++ unsigned int mask; ++ offsetT offset; ++ ++ cfi_add_advance_loc (p->prologue_sym); ++ ++ if (p->fp_regno != 30) ++ if (p->frame_size != 0) ++ cfi_add_CFA_def_cfa (p->fp_regno, p->frame_size); ++ else ++ cfi_add_CFA_def_cfa_register (p->fp_regno); ++ else if (p->frame_size != 0) ++ cfi_add_CFA_def_cfa_offset (p->frame_size); ++ ++ mask = p->mask; ++ offset = p->mask_offset; ++ ++ /* Recall that $26 is special-cased and stored first. */ ++ if ((mask >> 26) & 1) ++ { ++ cfi_add_CFA_offset (26, offset); ++ offset += 8; ++ mask &= ~(1 << 26); ++ } ++ while (mask) ++ { ++ unsigned int i; ++ i = mask & -mask; ++ mask ^= i; ++ i = ffs (i) - 1; ++ ++ cfi_add_CFA_offset (i, offset); ++ offset += 8; ++ } ++ ++ mask = p->fmask; ++ offset = p->fmask_offset; ++ while (mask) ++ { ++ unsigned int i; ++ i = mask & -mask; ++ mask ^= i; ++ i = ffs (i) - 1; ++ ++ cfi_add_CFA_offset (i + 32, offset); ++ offset += 8; ++ } ++ } ++ ++ cfi_end_fde (p->func_end_sym); ++ } + } + #endif /* OBJ_ELF */ + +--- gas/config/tc-alpha.h 7 Nov 2002 00:42:18 -0000 1.16 ++++ gas/config/tc-alpha.h 30 May 2003 03:01:11 -0000 1.17 +@@ -128,6 +128,11 @@ extern flagword alpha_elf_section_flags + #define tc_frob_file_before_fix() alpha_before_fix () + extern void alpha_before_fix PARAMS ((void)); + ++#ifdef OBJ_ELF ++#define md_end alpha_elf_md_end ++extern void alpha_elf_md_end PARAMS ((void)); ++#endif ++ + /* New fields for supporting explicit relocations (such as !literal to mark + where a pointer is loaded from the global table, and !lituse_base to track + all of the normal uses of that pointer). */ +@@ -156,4 +161,6 @@ do { \ + (long) FIX->tc_fix_data.next_reloc); \ + } while (0) + +-#define DWARF2_LINE_MIN_INSN_LENGTH 4 ++#define DWARF2_LINE_MIN_INSN_LENGTH 4 ++#define DWARF2_DEFAULT_RETURN_COLUMN 26 ++#define DWARF2_CIE_DATA_ALIGNMENT -8 +--- gas/config/tc-i386.c 20 May 2003 07:58:06 -0000 1.139 ++++ gas/config/tc-i386.c 27 May 2003 16:52:47 -0000 1.140 +@@ -319,6 +319,12 @@ static unsigned int no_cond_jump_promoti + /* Pre-defined "_GLOBAL_OFFSET_TABLE_". */ + symbolS *GOT_symbol; + ++/* The dwarf2 return column, adjusted for 32 or 64 bit. */ ++unsigned int x86_dwarf2_return_column; ++ ++/* The dwarf2 data alignment, adjusted for 32 or 64 bit. */ ++int x86_cie_data_alignment; ++ + /* Interface to relax_segment. + There are 3 major relax states for 386 jump insns because the + different types of jumps add different sizes to frags when we're +@@ -987,6 +993,17 @@ md_begin () + record_alignment (bss_section, 2); + } + #endif ++ ++ if (flag_code == CODE_64BIT) ++ { ++ x86_dwarf2_return_column = 16; ++ x86_cie_data_alignment = -8; ++ } ++ else ++ { ++ x86_dwarf2_return_column = 8; ++ x86_cie_data_alignment = -4; ++ } + } + + void +@@ -6301,42 +6318,15 @@ intel_putback_token () + prev_token.str = NULL; + } + +-void +-tc_x86_cfi_init (void) +-{ +- struct cfi_config cfi_config; +- +- if (flag_code == CODE_64BIT) +- { +- cfi_config.addr_length = 8; +- cfi_config.eh_align = 8; +- cfi_config.code_align = 1; +- cfi_config.data_align = -8; +- cfi_config.ra_column = 0x10; +- cfi_config.reloc_type = BFD_RELOC_64; +- } +- else +- { +- cfi_config.addr_length = 4; +- cfi_config.eh_align = 4; +- cfi_config.code_align = 1; +- cfi_config.data_align = -4; +- cfi_config.ra_column = 0x08; +- cfi_config.reloc_type = BFD_RELOC_32; +- } +- +- cfi_set_config (&cfi_config); +-} +- +-unsigned long ++int + tc_x86_regname_to_dw2regnum (const char *regname) + { + unsigned int regnum; + unsigned int regnames_count; + char *regnames_32[] = + { +- "eax", "ebx", "ecx", "edx", +- "edi", "esi", "ebp", "esp", ++ "eax", "ecx", "edx", "ebx", ++ "esp", "ebp", "esi", "edi", + "eip" + }; + char *regnames_64[] = +@@ -6364,21 +6354,18 @@ tc_x86_regname_to_dw2regnum (const char + if (strcmp (regname, regnames[regnum]) == 0) + return regnum; + +- as_bad (_("unknown register name '%s'"), regname); + return -1; + } + + void + tc_x86_frame_initial_instructions (void) + { +- if (flag_code == CODE_64BIT) +- { +- cfi_add_insn (CFA_def_cfa, tc_x86_regname_to_dw2regnum ("rsp"), 8); +- cfi_add_insn (CFA_offset, tc_x86_regname_to_dw2regnum ("rip"), -8); +- } +- else +- { +- cfi_add_insn (CFA_def_cfa, tc_x86_regname_to_dw2regnum ("esp"), 4); +- cfi_add_insn (CFA_offset, tc_x86_regname_to_dw2regnum ("eip"), -4); +- } ++ static unsigned int sp_regno; ++ ++ if (!sp_regno) ++ sp_regno = tc_x86_regname_to_dw2regnum (flag_code == CODE_64BIT ++ ? "rsp" : "esp"); ++ ++ cfi_add_CFA_def_cfa (sp_regno, -x86_cie_data_alignment); ++ cfi_add_CFA_offset (x86_dwarf2_return_column, x86_cie_data_alignment); + } +--- gas/config/tc-i386.h 20 May 2003 07:58:07 -0000 1.40 ++++ gas/config/tc-i386.h 27 May 2003 16:52:47 -0000 1.41 +@@ -546,18 +546,18 @@ extern void sco_id PARAMS ((void)); + #endif + + /* We want .cfi_* pseudo-ops for generating unwind info. */ +-#define TARGET_USE_CFIPOP +-#ifdef TARGET_USE_CFIPOP ++#define TARGET_USE_CFIPOP 1 + +-#define tc_cfi_init() tc_x86_cfi_init () +-extern void tc_x86_cfi_init PARAMS ((void)); ++extern unsigned int x86_dwarf2_return_column; ++#define DWARF2_DEFAULT_RETURN_COLUMN x86_dwarf2_return_column ++ ++extern int x86_cie_data_alignment; ++#define DWARF2_CIE_DATA_ALIGNMENT x86_cie_data_alignment + + #define tc_regname_to_dw2regnum tc_x86_regname_to_dw2regnum +-extern unsigned long tc_x86_regname_to_dw2regnum PARAMS ((const char *regname)); ++extern int tc_x86_regname_to_dw2regnum PARAMS ((const char *regname)); + + #define tc_cfi_frame_initial_instructions tc_x86_frame_initial_instructions + extern void tc_x86_frame_initial_instructions PARAMS ((void)); +- +-#endif /* TARGET_USE_CFIPOP */ + + #endif /* TC_I386 */ +--- gas/testsuite/gas/alpha/elf-reloc-8.d 7 Nov 2002 00:42:19 -0000 1.1 ++++ gas/testsuite/gas/alpha/elf-reloc-8.d 31 May 2003 19:36:45 -0000 1.3 +@@ -307,3 +307,24 @@ OFFSET *TYPE *VALUE + 0*0000048 REFQUAD \.init\.text\+0x0*00005f0 + 0*0000050 REFQUAD \.init\.data\+0x0*0000029 + 0*0000058 REFQUAD \.init\.text\+0x0*0000610 ++ ++ ++RELOCATION RECORDS FOR \[\.eh_frame\]: ++OFFSET *TYPE *VALUE ++0*000001c SREL32 \.init\.text ++0*0000034 SREL32 \.init\.text\+0x0*0000050 ++0*0000048 SREL32 \.init\.text\+0x0*0000080 ++0*000005c SREL32 \.init\.text\+0x0*00000b0 ++0*0000080 SREL32 \.init\.text\+0x0*00002c0 ++0*00000a0 SREL32 \.init\.text\+0x0*00005a0 ++0*00000b8 SREL32 \.init\.text\+0x0*00005f0 ++0*00000cc SREL32 \.init\.text\+0x0*0000610 ++0*00000e0 SREL32 \.init\.text\+0x0*0000630 ++0*00000fc SREL32 \.init\.text\+0x0*0000750 ++0*0000120 SREL32 \.init\.text\+0x0*0000990 ++0*000013c SREL32 \.init\.text\+0x0*0000a10 ++0*0000150 SREL32 \.init\.text\+0x0*0000a20 ++0*0000164 SREL32 \.init\.text\+0x0*0000a40 ++0*000017c SREL32 \.init\.text\+0x0*0000a90 ++0*0000190 SREL32 \.init\.text\+0x0*0000aa0 ++0*00001a4 SREL32 \.text +--- gas/testsuite/gas/cfi/cfi-i386.d 20 May 2003 14:31:44 -0000 1.2 ++++ gas/testsuite/gas/cfi/cfi-i386.d 27 May 2003 16:52:49 -0000 1.3 +@@ -2,50 +2,46 @@ + #name: CFI on i386 + The section .eh_frame contains: + +-00000000 00000010 00000000 CIE ++00000000 00000014 00000000 CIE + Version: 1 +- Augmentation: "" ++ Augmentation: "zR" + Code alignment factor: 1 + Data alignment factor: -4 + Return address column: 8 ++ Augmentation data: 1b + +- DW_CFA_def_cfa: r7 ofs 4 ++ DW_CFA_def_cfa: r4 ofs 4 + DW_CFA_offset: r8 at cfa-4 + DW_CFA_nop + DW_CFA_nop + +-00000014 00000014 00000018 FDE cie=00000000 pc=00000000..00000012 +- DW_CFA_advance_loc: 6 to 00000006 ++00000018 00000014 0000001c FDE cie=00000000 pc=00000020..00000032 ++ DW_CFA_advance_loc: 6 to 00000026 + DW_CFA_def_cfa_offset: 4664 +- DW_CFA_advance_loc: 11 to 00000011 ++ DW_CFA_advance_loc: 11 to 00000031 + DW_CFA_def_cfa_offset: 4 +- DW_CFA_nop + +-0000002c 00000018 00000030 FDE cie=00000000 pc=00000012..0000001f +- DW_CFA_advance_loc: 1 to 00000013 ++00000030 00000018 00000034 FDE cie=00000000 pc=0000004a..00000057 ++ DW_CFA_advance_loc: 1 to 0000004b + DW_CFA_def_cfa_offset: 8 +- DW_CFA_offset: r6 at cfa-8 +- DW_CFA_advance_loc: 2 to 00000015 +- DW_CFA_def_cfa_reg: r6 +- DW_CFA_advance_loc: 9 to 0000001e +- DW_CFA_def_cfa_reg: r7 +- DW_CFA_nop ++ DW_CFA_offset: r5 at cfa-8 ++ DW_CFA_advance_loc: 2 to 0000004d ++ DW_CFA_def_cfa_reg: r5 ++ DW_CFA_advance_loc: 9 to 00000056 ++ DW_CFA_def_cfa_reg: r4 + +-00000048 00000014 0000004c FDE cie=00000000 pc=0000001f..0000002f +- DW_CFA_advance_loc: 2 to 00000021 +- DW_CFA_def_cfa_reg: r1 +- DW_CFA_advance_loc: 13 to 0000002e +- DW_CFA_def_cfa: r7 ofs 4 +- DW_CFA_nop ++0000004c 00000014 00000050 FDE cie=00000000 pc=00000073..00000083 ++ DW_CFA_advance_loc: 2 to 00000075 ++ DW_CFA_def_cfa_reg: r3 ++ DW_CFA_advance_loc: 13 to 00000082 ++ DW_CFA_def_cfa: r4 ofs 4 + +-00000060 00000010 00000064 FDE cie=00000000 pc=0000002f..00000035 +- DW_CFA_nop ++00000064 00000010 00000068 FDE cie=00000000 pc=0000009b..000000a1 + DW_CFA_nop + DW_CFA_nop + DW_CFA_nop + +-00000074 00000010 00000078 FDE cie=00000000 pc=00000035..00000044 +- DW_CFA_nop ++00000078 00000010 0000007c FDE cie=00000000 pc=000000b5..000000c4 + DW_CFA_nop + DW_CFA_nop + DW_CFA_nop +--- gas/testsuite/gas/cfi/cfi-x86_64.d 20 May 2003 14:31:44 -0000 1.2 ++++ gas/testsuite/gas/cfi/cfi-x86_64.d 27 May 2003 16:52:49 -0000 1.3 +@@ -1,68 +1,51 @@ + #readelf: -wf + #name: CFI on x86-64 +- + The section .eh_frame contains: + + 00000000 00000014 00000000 CIE + Version: 1 +- Augmentation: "" ++ Augmentation: "zR" + Code alignment factor: 1 + Data alignment factor: -8 + Return address column: 16 ++ Augmentation data: 1b + + DW_CFA_def_cfa: r7 ofs 8 + DW_CFA_offset: r16 at cfa-8 + DW_CFA_nop + DW_CFA_nop +- DW_CFA_nop +- DW_CFA_nop +- DW_CFA_nop +- DW_CFA_nop + +-00000018 0000001c 0000001c FDE cie=00000000 pc=00000000..00000014 +- DW_CFA_advance_loc: 7 to 00000007 ++00000018 00000014 0000001c FDE cie=00000000 pc=00000020..00000034 ++ DW_CFA_advance_loc: 7 to 00000027 + DW_CFA_def_cfa_offset: 4668 +- DW_CFA_advance_loc: 12 to 00000013 ++ DW_CFA_advance_loc: 12 to 00000033 + DW_CFA_def_cfa_offset: 8 +- DW_CFA_nop + +-00000038 00000024 0000003c FDE cie=00000000 pc=00000000..0000000f +- DW_CFA_advance_loc: 1 to 00000001 ++00000030 0000001c 00000034 FDE cie=00000000 pc=00000038..00000047 ++ DW_CFA_advance_loc: 1 to 00000039 + DW_CFA_def_cfa_offset: 16 + DW_CFA_offset: r6 at cfa-16 +- DW_CFA_advance_loc: 3 to 00000004 ++ DW_CFA_advance_loc: 3 to 0000003c + DW_CFA_def_cfa_reg: r6 +- DW_CFA_advance_loc: 10 to 0000000e ++ DW_CFA_advance_loc: 10 to 00000046 + DW_CFA_def_cfa: r7 ofs 8 + DW_CFA_nop + DW_CFA_nop + DW_CFA_nop +- DW_CFA_nop + +-00000060 0000001c 00000064 FDE cie=00000000 pc=00000000..00000013 +- DW_CFA_advance_loc: 3 to 00000003 ++00000050 00000014 00000054 FDE cie=00000000 pc=00000058..0000006b ++ DW_CFA_advance_loc: 3 to 0000005b + DW_CFA_def_cfa_reg: r12 +- DW_CFA_advance_loc: 15 to 00000012 ++ DW_CFA_advance_loc: 15 to 0000006a + DW_CFA_def_cfa_reg: r7 + DW_CFA_nop +- DW_CFA_nop + +-00000080 0000001c 00000084 FDE cie=00000000 pc=00000000..00000006 +- DW_CFA_nop +- DW_CFA_nop +- DW_CFA_nop +- DW_CFA_nop +- DW_CFA_nop ++00000068 00000010 0000006c FDE cie=00000000 pc=00000070..00000076 + DW_CFA_nop + DW_CFA_nop + DW_CFA_nop + +-000000a0 0000001c 000000a4 FDE cie=00000000 pc=00000000..00000012 +- DW_CFA_nop +- DW_CFA_nop +- DW_CFA_nop +- DW_CFA_nop +- DW_CFA_nop ++0000007c 00000010 00000080 FDE cie=00000000 pc=00000084..00000096 + DW_CFA_nop + DW_CFA_nop + DW_CFA_nop +--- gas/testsuite/gas/cfi/cfi.exp 20 May 2003 08:01:19 -0000 1.1 ++++ gas/testsuite/gas/cfi/cfi.exp 31 May 2003 19:36:45 -0000 1.3 +@@ -5,3 +5,16 @@ if [istarget "x86_64-*"] then { + if [istarget "i?86-*"] then { + run_dump_test "cfi-i386" + } ++ ++if { [istarget alpha*-*-*] } then { ++ ++ set elf [expr [istarget *-*-elf*] \ ++ || [istarget *-*-linux*] \ ++ || [istarget *-*-freebsd*] \ ++ || [istarget *-*-netbsd*] ] ++ ++ if $elf { ++ run_dump_test "cfi-alpha-1" ++ run_dump_test "cfi-alpha-2" ++ } ++} +--- gas/testsuite/gas/cfi/cfi-alpha-1.d 2003-01-30 05:24:37.000000000 -0500 ++++ gas/testsuite/gas/cfi/cfi-alpha-1.d 2003-05-29 23:01:12.000000000 -0400 +@@ -0,0 +1,26 @@ ++#readelf: -wf ++#name: CFI on alpha ++The section .eh_frame contains: ++ ++00000000 00000010 00000000 CIE ++ Version: 1 ++ Augmentation: "zR" ++ Code alignment factor: 4 ++ Data alignment factor: -8 ++ Return address column: 26 ++ Augmentation data: 1b ++ ++ DW_CFA_def_cfa_reg: r30 ++ DW_CFA_nop ++ ++00000014 0000001c 00000018 FDE cie=00000000 pc=0000001c..00000050 ++ DW_CFA_advance_loc: 24 to 00000034 ++ DW_CFA_def_cfa: r15 ofs 32 ++ DW_CFA_offset: r26 at cfa-32 ++ DW_CFA_offset: r9 at cfa-24 ++ DW_CFA_offset: r15 at cfa-16 ++ DW_CFA_offset: r34 at cfa-8 ++ DW_CFA_nop ++ DW_CFA_nop ++ DW_CFA_nop ++ +--- gas/testsuite/gas/cfi/cfi-alpha-1.s 2003-01-30 05:24:37.000000000 -0500 ++++ gas/testsuite/gas/cfi/cfi-alpha-1.s 2003-05-29 23:01:12.000000000 -0400 +@@ -0,0 +1,28 @@ ++ .file 1 "z.c" ++ .set noat ++ .set noreorder ++.text ++ .align 4 ++ .globl f ++ .ent f ++$f..ng: ++f: ++ .frame $15,32,$26,0 ++ .mask 0x4008200,-32 ++ .fmask 0x4,-8 ++ lda $30,-32($30) ++ stq $26,0($30) ++ stq $9,8($30) ++ stq $15,16($30) ++ stt $f2,24($30) ++ mov $30,$15 ++ .prologue 0 ++ mov $15,$30 ++ ldq $26,0($30) ++ ldq $9,8($30) ++ ldt $f2,24($30) ++ ldq $15,16($30) ++ lda $30,32($30) ++ ret $31,($26),1 ++ .end f ++ .ident "GCC: (GNU) 2.96 20000731 (Red Hat Linux 7.2 2.96-112.7.1)" +--- gas/testsuite/gas/cfi/cfi-alpha-2.d 2003-01-30 05:24:37.000000000 -0500 ++++ gas/testsuite/gas/cfi/cfi-alpha-2.d 2003-05-31 15:36:45.000000000 -0400 +@@ -0,0 +1,9 @@ ++#objdump: -r -j .eh_frame ++#name: CFI on alpha, 2 ++ ++.*: file format elf64-alpha ++ ++RELOCATION RECORDS FOR \[\.eh_frame\]: ++OFFSET TYPE VALUE ++0*000001c SREL32 \.text ++0*0000030 SREL32 \.text\+0x0*0000004 +--- gas/testsuite/gas/cfi/cfi-alpha-2.s 2003-01-30 05:24:37.000000000 -0500 ++++ gas/testsuite/gas/cfi/cfi-alpha-2.s 2003-05-31 15:36:45.000000000 -0400 +@@ -0,0 +1,14 @@ ++ .text ++ .ent foo ++foo: ++ .frame $30, 0, $26, 0 ++ .prologue 1 ++ ret ++ .end foo ++ ++ .ent bar ++bar: ++ .frame $30, 0, $26, 0 ++ .prologue 1 ++ ret ++ .end bar +--- gas/testsuite/gas/cfi/cfi-i386-2.d 2003-01-30 05:24:37.000000000 -0500 ++++ gas/testsuite/gas/cfi/cfi-i386-2.d 2003-05-27 12:52:49.000000000 -0400 +@@ -0,0 +1,26 @@ ++#readelf: -wf ++#name: CFI on i386, 2 ++The section .eh_frame contains: ++ ++00000000 00000014 00000000 CIE ++ Version: 1 ++ Augmentation: "zR" ++ Code alignment factor: 1 ++ Data alignment factor: -4 ++ Return address column: 8 ++ Augmentation data: 1b ++ ++ DW_CFA_def_cfa: r4 ofs 4 ++ DW_CFA_offset: r8 at cfa-4 ++ DW_CFA_nop ++ DW_CFA_nop ++ ++00000018 00000018 0000001c FDE cie=00000000 pc=00000020..00000029 ++ DW_CFA_advance_loc: 1 to 00000021 ++ DW_CFA_def_cfa_offset: 8 ++ DW_CFA_offset: r5 at cfa-8 ++ DW_CFA_advance_loc: 4 to 00000025 ++ DW_CFA_offset: r3 at cfa-12 ++ DW_CFA_def_cfa_offset: 12 ++ DW_CFA_nop ++ +--- gas/testsuite/gas/cfi/cfi-i386-2.s 2003-01-30 05:24:37.000000000 -0500 ++++ gas/testsuite/gas/cfi/cfi-i386-2.s 2003-05-27 12:52:49.000000000 -0400 +@@ -0,0 +1,17 @@ ++ .text ++ .globl foo ++ .type foo,@function ++ .cfi_startproc ++foo: ++ push %ebp ++ .cfi_adjust_cfa_offset 4 ++ .cfi_offset %ebp, -8 ++ .align 4 ++ push %ebx ++ .cfi_offset %ebx, -12 ++ .cfi_adjust_cfa_offset 4 ++ nop ++ pop %ebx ++ pop %ebp ++ ret ++ .cfi_endproc diff --git a/sys-devel/binutils/files/2.14/binutils-2.14.90.0.4-cfi2.patch b/sys-devel/binutils/files/2.14/binutils-2.14.90.0.4-cfi2.patch new file mode 100644 index 000000000000..374fe9418bb1 --- /dev/null +++ b/sys-devel/binutils/files/2.14/binutils-2.14.90.0.4-cfi2.patch @@ -0,0 +1,651 @@ +2003-06-05 Michal Ludvig <mludvig@suse.cz> + + * dw2gencfi.c (cfi_add_CFA_insn, cfi_add_CFA_insn_reg) + (cfi_add_CFA_insn_reg_reg, cfi_add_CFA_insn_reg_offset): New. + (cfi_add_CFA_offset, cfi_add_CFA_def_cfa) + (cfi_add_CFA_register, cfi_add_CFA_def_cfa_register) + (cfi_add_CFA_def_cfa_offset): Use cfi_add_CFA_insn_*(). + (cfi_add_CFA_restore, cfi_add_CFA_undefined) + (cfi_add_CFA_same_value, cfi_add_CFA_remember_state) + (cfi_add_CFA_restore_state, cfi_add_CFA_nop): New. + (cfi_pseudo_table): New directives .cfi_return_column, + .cfi_restore, .cfi_undefined, .cfi_same_value, + .cfi_remember_state, .cfi_restore_state, .cfi_nop. + (dot_cfi, output_cfi_insn): Handle new directives. + * dw2gencfi.h (cfi_add_CFA_restore, cfi_add_CFA_undefined) + (cfi_add_CFA_same_value, cfi_add_CFA_remember_state) + (cfi_add_CFA_restore_state, cfi_add_CFA_nop): New prototypes. + +2003-06-04 Richard Henderson <rth@redhat.com> + + * dw2gencfi.c (output_cfi_insn): Fix typo for negative offsets. + + * dw2gencfi.c (cfi_finish): Set .eh_frame read-only. + +2003-06-04 Richard Henderson <rth@redhat.com> + + * config/tc-alpha.c (s_alpha_usepv): New. + (md_pseudo_table): Add it. + (alpha_cfi_frame_initial_instructions): New. + * config/tc-alpha.h (TARGET_USE_CFIPOP): New. + (tc_cfi_frame_initial_instructions): New. + * doc/c-alpha.texi: Document .usepv. + +testsuite/ +2003-06-04 Richard Henderson <rth@redhat.com> + + * gas/alpha/elf-usepv-1.[sd]: New. + * gas/alpha/elf-usepv-2.[sd]: New. + * gas/alpha/alpha.exp: Run them. + * gas/cfi/cfi-alpha-3.[sd]: New. + * gas/cfi/cfi.exp: Run it. + +--- gas/dw2gencfi.c 2 Jun 2003 22:48:59 -0000 1.7 ++++ gas/dw2gencfi.c 5 Jun 2003 09:23:47 -0000 1.10 +@@ -164,6 +164,54 @@ cfi_set_return_column (unsigned regno) + cur_fde_data->return_column = regno; + } + ++/* Universal functions to store new instructions. */ ++ ++static void ++cfi_add_CFA_insn(int insn) ++{ ++ struct cfi_insn_data *insn_ptr = alloc_cfi_insn_data (); ++ ++ insn_ptr->insn = insn; ++} ++ ++static void ++cfi_add_CFA_insn_reg (int insn, unsigned regno) ++{ ++ struct cfi_insn_data *insn_ptr = alloc_cfi_insn_data (); ++ ++ insn_ptr->insn = insn; ++ insn_ptr->u.r = regno; ++} ++ ++static void ++cfi_add_CFA_insn_offset (int insn, offsetT offset) ++{ ++ struct cfi_insn_data *insn_ptr = alloc_cfi_insn_data (); ++ ++ insn_ptr->insn = insn; ++ insn_ptr->u.i = offset; ++} ++ ++static void ++cfi_add_CFA_insn_reg_reg (int insn, unsigned reg1, unsigned reg2) ++{ ++ struct cfi_insn_data *insn_ptr = alloc_cfi_insn_data (); ++ ++ insn_ptr->insn = insn; ++ insn_ptr->u.rr.reg1 = reg1; ++ insn_ptr->u.rr.reg2 = reg2; ++} ++ ++static void ++cfi_add_CFA_insn_reg_offset (int insn, unsigned regno, offsetT offset) ++{ ++ struct cfi_insn_data *insn_ptr = alloc_cfi_insn_data (); ++ ++ insn_ptr->insn = insn; ++ insn_ptr->u.ri.reg = regno; ++ insn_ptr->u.ri.offset = offset; ++} ++ + /* Add a CFI insn to advance the PC from the last address to LABEL. */ + + void +@@ -183,11 +231,7 @@ cfi_add_advance_loc (symbolS *label) + void + cfi_add_CFA_offset (unsigned regno, offsetT offset) + { +- struct cfi_insn_data *insn = alloc_cfi_insn_data (); +- +- insn->insn = DW_CFA_offset; +- insn->u.ri.reg = regno; +- insn->u.ri.offset = offset; ++ cfi_add_CFA_insn_reg_offset (DW_CFA_offset, regno, offset); + } + + /* Add a DW_CFA_def_cfa record to the CFI data. */ +@@ -195,12 +239,7 @@ cfi_add_CFA_offset (unsigned regno, offs + void + cfi_add_CFA_def_cfa (unsigned regno, offsetT offset) + { +- struct cfi_insn_data *insn = alloc_cfi_insn_data (); +- +- insn->insn = DW_CFA_def_cfa; +- insn->u.ri.reg = regno; +- insn->u.ri.offset = offset; +- ++ cfi_add_CFA_insn_reg_offset (DW_CFA_def_cfa, regno, offset); + cur_cfa_offset = offset; + } + +@@ -209,11 +248,7 @@ cfi_add_CFA_def_cfa (unsigned regno, off + void + cfi_add_CFA_register (unsigned reg1, unsigned reg2) + { +- struct cfi_insn_data *insn = alloc_cfi_insn_data (); +- +- insn->insn = DW_CFA_register; +- insn->u.rr.reg1 = reg1; +- insn->u.rr.reg2 = reg2; ++ cfi_add_CFA_insn_reg_reg (DW_CFA_register, reg1, reg2); + } + + /* Add a DW_CFA_def_cfa_register record to the CFI data. */ +@@ -221,10 +256,7 @@ cfi_add_CFA_register (unsigned reg1, uns + void + cfi_add_CFA_def_cfa_register (unsigned regno) + { +- struct cfi_insn_data *insn = alloc_cfi_insn_data (); +- +- insn->insn = DW_CFA_def_cfa_register; +- insn->u.r = regno; ++ cfi_add_CFA_insn_reg (DW_CFA_def_cfa_register, regno); + } + + /* Add a DW_CFA_def_cfa_offset record to the CFI data. */ +@@ -232,14 +264,46 @@ cfi_add_CFA_def_cfa_register (unsigned r + void + cfi_add_CFA_def_cfa_offset (offsetT offset) + { +- struct cfi_insn_data *insn = alloc_cfi_insn_data (); +- +- insn->insn = DW_CFA_def_cfa_offset; +- insn->u.i = offset; +- ++ cfi_add_CFA_insn_offset (DW_CFA_def_cfa_offset, offset); + cur_cfa_offset = offset; + } + ++void ++cfi_add_CFA_restore (unsigned regno) ++{ ++ cfi_add_CFA_insn_reg (DW_CFA_restore, regno); ++} ++ ++void ++cfi_add_CFA_undefined (unsigned regno) ++{ ++ cfi_add_CFA_insn_reg (DW_CFA_undefined, regno); ++} ++ ++void ++cfi_add_CFA_same_value (unsigned regno) ++{ ++ cfi_add_CFA_insn_reg (DW_CFA_same_value, regno); ++} ++ ++void ++cfi_add_CFA_remember_state (void) ++{ ++ cfi_add_CFA_insn (DW_CFA_remember_state); ++} ++ ++void ++cfi_add_CFA_restore_state (void) ++{ ++ cfi_add_CFA_insn (DW_CFA_restore_state); ++} ++ ++void ++cfi_add_CFA_nop (void) ++{ ++ cfi_add_CFA_insn (DW_CFA_nop); ++} ++ + + /* Parse CFI assembler directives. */ + +@@ -248,7 +312,8 @@ static void dot_cfi_startproc (int); + static void dot_cfi_endproc (int); + + /* Fake CFI type; outside the byte range of any real CFI insn. */ +-#define CFI_adjust_cfa_offset 0x100 ++#define CFI_adjust_cfa_offset 0x100 ++#define CFI_return_column 0x101 + + const pseudo_typeS cfi_pseudo_table[] = + { +@@ -260,6 +325,13 @@ const pseudo_typeS cfi_pseudo_table[] = + { "cfi_adjust_cfa_offset", dot_cfi, CFI_adjust_cfa_offset }, + { "cfi_offset", dot_cfi, DW_CFA_offset }, + { "cfi_register", dot_cfi, DW_CFA_register }, ++ { "cfi_return_column", dot_cfi, CFI_return_column }, ++ { "cfi_restore", dot_cfi, DW_CFA_restore }, ++ { "cfi_undefined", dot_cfi, DW_CFA_undefined }, ++ { "cfi_same_value", dot_cfi, DW_CFA_same_value }, ++ { "cfi_remember_state", dot_cfi, DW_CFA_remember_state }, ++ { "cfi_restore_state", dot_cfi, DW_CFA_restore_state }, ++ { "cfi_nop", dot_cfi, DW_CFA_nop }, + { NULL, NULL, 0 } + }; + +@@ -343,46 +415,74 @@ dot_cfi (int arg) + + switch (arg) + { +- /* Instructions that take two arguments (register, integer). */ + case DW_CFA_offset: +- case DW_CFA_def_cfa: + reg1 = cfi_parse_reg (); + cfi_parse_separator (); + offset = cfi_parse_const (); ++ cfi_add_CFA_offset (reg1, offset); ++ break; + +- if (arg == DW_CFA_def_cfa) +- cfi_add_CFA_def_cfa (reg1, offset); +- else +- cfi_add_CFA_offset (reg1, offset); ++ case DW_CFA_def_cfa: ++ reg1 = cfi_parse_reg (); ++ cfi_parse_separator (); ++ offset = cfi_parse_const (); ++ cfi_add_CFA_def_cfa (reg1, offset); + break; + +- /* Instructions that take two arguments (register, register). */ + case DW_CFA_register: + reg1 = cfi_parse_reg (); + cfi_parse_separator (); + reg2 = cfi_parse_reg (); +- + cfi_add_CFA_register (reg1, reg2); + break; + +- /* Instructions that take one register argument. */ + case DW_CFA_def_cfa_register: + reg1 = cfi_parse_reg (); + cfi_add_CFA_def_cfa_register (reg1); + break; + +- /* Instructions that take one integer argument. */ + case DW_CFA_def_cfa_offset: + offset = cfi_parse_const (); + cfi_add_CFA_def_cfa_offset (offset); + break; + +- /* Special handling for pseudo-instruction. */ + case CFI_adjust_cfa_offset: + offset = cfi_parse_const (); + cfi_add_CFA_def_cfa_offset (cur_cfa_offset + offset); + break; + ++ case DW_CFA_restore: ++ reg1 = cfi_parse_reg (); ++ cfi_add_CFA_restore (reg1); ++ break; ++ ++ case DW_CFA_undefined: ++ reg1 = cfi_parse_reg (); ++ cfi_add_CFA_undefined (reg1); ++ break; ++ ++ case DW_CFA_same_value: ++ reg1 = cfi_parse_reg (); ++ cfi_add_CFA_same_value (reg1); ++ break; ++ ++ case CFI_return_column: ++ reg1 = cfi_parse_reg (); ++ cfi_set_return_column (reg1); ++ break; ++ ++ case DW_CFA_remember_state: ++ cfi_add_CFA_remember_state (); ++ break; ++ ++ case DW_CFA_restore_state: ++ cfi_add_CFA_restore_state (); ++ break; ++ ++ case DW_CFA_nop: ++ cfi_add_CFA_nop (); ++ break; ++ + default: + abort (); + } +@@ -553,8 +653,10 @@ output_cfi_insn (struct cfi_insn_data *i + break; + + case DW_CFA_def_cfa_register: +- out_one (DW_CFA_def_cfa_register); +- out_uleb128 (insn->u.i); ++ case DW_CFA_undefined: ++ case DW_CFA_same_value: ++ out_one (insn->insn); ++ out_uleb128 (insn->u.r); + break; + + case DW_CFA_def_cfa_offset: +@@ -571,12 +673,25 @@ output_cfi_insn (struct cfi_insn_data *i + } + break; + ++ case DW_CFA_restore: ++ regno = insn->u.r; ++ if (regno <= 0x3F) ++ { ++ out_one (DW_CFA_restore + regno); ++ } ++ else ++ { ++ out_one (DW_CFA_restore_extended); ++ out_uleb128 (regno); ++ } ++ break; ++ + case DW_CFA_offset: + regno = insn->u.ri.reg; + offset = insn->u.ri.offset / DWARF2_CIE_DATA_ALIGNMENT; + if (offset < 0) + { +- out_one (DW_CFA_offset_extended); ++ out_one (DW_CFA_offset_extended_sf); + out_uleb128 (regno); + out_sleb128 (offset); + } +@@ -599,8 +714,10 @@ output_cfi_insn (struct cfi_insn_data *i + out_uleb128 (insn->u.rr.reg2); + break; + ++ case DW_CFA_remember_state: ++ case DW_CFA_restore_state: + case DW_CFA_nop: +- out_one (DW_CFA_nop); ++ out_one (insn->insn); + break; + + default: +@@ -722,6 +839,9 @@ select_cie_for_fde (struct fde_entry *fd + break; + + case DW_CFA_def_cfa_register: ++ case DW_CFA_restore: ++ case DW_CFA_undefined: ++ case DW_CFA_same_value: + if (i->u.r != j->u.r) + goto fail; + break; +@@ -785,7 +905,7 @@ cfi_finish (void) + cfi_seg = subseg_new (".eh_frame", 0); + #ifdef BFD_ASSEMBLER + bfd_set_section_flags (stdoutput, cfi_seg, +- SEC_ALLOC | SEC_LOAD | SEC_RELOC | SEC_DATA); ++ SEC_ALLOC | SEC_LOAD | SEC_DATA | SEC_READONLY); + #endif + subseg_set (cfi_seg, 0); + record_alignment (cfi_seg, 2); +--- gas/dw2gencfi.h 27 May 2003 16:52:46 -0000 1.2 ++++ gas/dw2gencfi.h 5 Jun 2003 09:23:47 -0000 1.3 +@@ -37,10 +37,17 @@ extern void cfi_new_fde (struct symbol * + extern void cfi_end_fde (struct symbol *); + extern void cfi_set_return_column (unsigned); + extern void cfi_add_advance_loc (struct symbol *); ++ + extern void cfi_add_CFA_offset (unsigned, offsetT); + extern void cfi_add_CFA_def_cfa (unsigned, offsetT); + extern void cfi_add_CFA_register (unsigned, unsigned); + extern void cfi_add_CFA_def_cfa_register (unsigned); + extern void cfi_add_CFA_def_cfa_offset (offsetT); ++extern void cfi_add_CFA_restore (unsigned); ++extern void cfi_add_CFA_undefined (unsigned); ++extern void cfi_add_CFA_same_value (unsigned); ++extern void cfi_add_CFA_remember_state (void); ++extern void cfi_add_CFA_restore_state (void); ++extern void cfi_add_CFA_nop (void); + + #endif /* DW2GENCFI_H */ +--- gas/config/tc-alpha.c 30 May 2003 03:01:11 -0000 1.57 ++++ gas/config/tc-alpha.c 5 Jun 2003 03:27:03 -0000 1.58 +@@ -267,6 +267,7 @@ static void s_alpha_file PARAMS ((int)); + static void s_alpha_loc PARAMS ((int)); + static void s_alpha_stab PARAMS ((int)); + static void s_alpha_coff_wrapper PARAMS ((int)); ++static void s_alpha_usepv PARAMS ((int)); + #endif + #ifdef OBJ_EVAX + static void s_alpha_section PARAMS ((int)); +@@ -4822,8 +4823,65 @@ alpha_elf_md_end (void) + cfi_end_fde (p->func_end_sym); + } + } ++ ++static void ++s_alpha_usepv (int unused ATTRIBUTE_UNUSED) ++{ ++ char *name, name_end; ++ char *which, which_end; ++ symbolS *sym; ++ int other; ++ ++ name = input_line_pointer; ++ name_end = get_symbol_end (); ++ ++ if (! is_name_beginner (*name)) ++ { ++ as_bad (_(".usepv directive has no name")); ++ *input_line_pointer = name_end; ++ ignore_rest_of_line (); ++ return; ++ } ++ ++ sym = symbol_find_or_make (name); ++ *input_line_pointer++ = name_end; ++ ++ if (name_end != ',') ++ { ++ as_bad (_(".usepv directive has no type")); ++ ignore_rest_of_line (); ++ return; ++ } ++ ++ SKIP_WHITESPACE (); ++ which = input_line_pointer; ++ which_end = get_symbol_end (); ++ ++ if (strcmp (which, "no") == 0) ++ other = STO_ALPHA_NOPV; ++ else if (strcmp (which, "std") == 0) ++ other = STO_ALPHA_STD_GPLOAD; ++ else ++ { ++ as_bad (_("unknown argument for .usepv")); ++ other = 0; ++ } ++ ++ *input_line_pointer = which_end; ++ demand_empty_rest_of_line (); ++ ++ S_SET_OTHER (sym, other | (S_GET_OTHER (sym) & ~STO_ALPHA_STD_GPLOAD)); ++} + #endif /* OBJ_ELF */ + ++/* Standard calling conventions leaves the CFA at $30 on entry. */ ++ ++void ++alpha_cfi_frame_initial_instructions () ++{ ++ cfi_add_CFA_def_cfa_register (30); ++} ++ + #ifdef OBJ_EVAX + + /* Handle the section specific pseudo-op. */ +@@ -5669,6 +5727,7 @@ const pseudo_typeS md_pseudo_table[] = { + {"loc", s_alpha_loc, 9}, + {"stabs", s_alpha_stab, 's'}, + {"stabn", s_alpha_stab, 'n'}, ++ {"usepv", s_alpha_usepv, 0}, + /* COFF debugging related pseudos. */ + {"begin", s_alpha_coff_wrapper, 0}, + {"bend", s_alpha_coff_wrapper, 1}, +--- gas/config/tc-alpha.h 30 May 2003 03:01:11 -0000 1.17 ++++ gas/config/tc-alpha.h 5 Jun 2003 03:27:03 -0000 1.18 +@@ -161,6 +161,11 @@ do { \ + (long) FIX->tc_fix_data.next_reloc); \ + } while (0) + ++#define TARGET_USE_CFIPOP 1 ++ ++#define tc_cfi_frame_initial_instructions alpha_cfi_frame_initial_instructions ++extern void alpha_cfi_frame_initial_instructions(void); ++ + #define DWARF2_LINE_MIN_INSN_LENGTH 4 + #define DWARF2_DEFAULT_RETURN_COLUMN 26 + #define DWARF2_CIE_DATA_ALIGNMENT -8 +--- gas/doc/c-alpha.texi 19 Dec 2002 01:11:31 -0000 1.4 ++++ gas/doc/c-alpha.texi 5 Jun 2003 03:27:03 -0000 1.5 +@@ -379,6 +379,18 @@ to perform a load of the GP register; 2 + used in some non-standard way and so the linker cannot elide the load of + the procedure vector during relaxation. + ++@item .usepv @var{function}, @var{which} ++Used to indicate the use of the @code{$27} register, similar to ++@code{.prologue}, but without the other semantics of needing to ++be inside an open @code{.ent}/@code{.end} block. ++ ++The @var{which} argument should be either @code{no}, indicating that ++@code{$27} is not used, or @code{std}, indicating that the first two ++instructions of the function perform a GP load. ++ ++One might use this directive instead of @code{.prologue} if you are ++also using dwarf2 CFI directives. ++ + @item .gprel32 @var{expression} + Computes the difference between the address in @var{expression} and the + GP for the current object file, and stores it in 4 bytes. In addition + +--- gas/testsuite/gas/alpha/alpha.exp 7 Nov 2002 00:42:18 -0000 1.6 ++++ gas/testsuite/gas/alpha/alpha.exp 5 Jun 2003 03:27:03 -0000 1.7 +@@ -34,6 +34,8 @@ if { [istarget alpha*-*-*] } then { + run_dump_test "elf-tls-1" + run_list_test "elf-tls-2" "" + run_list_test "elf-tls-3" "" ++ run_dump_test "elf-usepv-1" ++ run_list_test "elf-usepv-2" "" + } + + run_dump_test "fp" +--- gas/testsuite/gas/cfi/cfi.exp 31 May 2003 19:36:45 -0000 1.3 ++++ gas/testsuite/gas/cfi/cfi.exp 5 Jun 2003 03:27:03 -0000 1.4 +@@ -16,5 +16,6 @@ if { [istarget alpha*-*-*] } then { + if $elf { + run_dump_test "cfi-alpha-1" + run_dump_test "cfi-alpha-2" ++ run_dump_test "cfi-alpha-3" + } + } +--- gas/testsuite/gas/alpha/elf-usepv-1.d 2003-01-30 05:24:37.000000000 -0500 ++++ gas/testsuite/gas/alpha/elf-usepv-1.d 2003-06-04 23:27:03.000000000 -0400 +@@ -0,0 +1,11 @@ ++#objdump: --syms ++#name: alpha elf-usepv-1 ++ ++.*: file format elf64-alpha ++ ++SYMBOL TABLE: ++0*0000000 l d .text 0*0000000 ++0*0000000 l d .data 0*0000000 ++0*0000000 l d .bss 0*0000000 ++0*0000000 l .text 0*0000000 0x80 foo ++0*0000004 l .text 0*0000000 0x88 bar +--- gas/testsuite/gas/alpha/elf-usepv-1.s 2003-01-30 05:24:37.000000000 -0500 ++++ gas/testsuite/gas/alpha/elf-usepv-1.s 2003-06-04 23:27:03.000000000 -0400 +@@ -0,0 +1,6 @@ ++ .usepv foo, no ++foo: ++ nop ++ .usepv bar, std ++bar: ++ nop +--- gas/testsuite/gas/alpha/elf-usepv-2.l 2003-01-30 05:24:37.000000000 -0500 ++++ gas/testsuite/gas/alpha/elf-usepv-2.l 2003-06-04 23:27:03.000000000 -0400 +@@ -0,0 +1,2 @@ ++.*: Assembler messages: ++.*:1: Error: unknown argument for .usepv +--- gas/testsuite/gas/alpha/elf-usepv-2.s 2003-01-30 05:24:37.000000000 -0500 ++++ gas/testsuite/gas/alpha/elf-usepv-2.s 2003-06-04 23:27:03.000000000 -0400 +@@ -0,0 +1 @@ ++ .usepv foo, bar +--- gas/testsuite/gas/cfi/cfi-alpha-3.d 2003-01-30 05:24:37.000000000 -0500 ++++ gas/testsuite/gas/cfi/cfi-alpha-3.d 2003-06-04 23:27:03.000000000 -0400 +@@ -0,0 +1,32 @@ ++#readelf: -wf ++#name: CFI on alpha, 3 ++The section .eh_frame contains: ++ ++00000000 00000010 00000000 CIE ++ Version: 1 ++ Augmentation: "zR" ++ Code alignment factor: 4 ++ Data alignment factor: -8 ++ Return address column: 26 ++ Augmentation data: 1b ++ ++ DW_CFA_def_cfa_reg: r30 ++ DW_CFA_nop ++ ++00000014 00000024 00000018 FDE cie=00000000 pc=0000001c..0000005c ++ DW_CFA_advance_loc: 4 to 00000020 ++ DW_CFA_def_cfa_offset: 32 ++ DW_CFA_advance_loc: 4 to 00000024 ++ DW_CFA_offset: r26 at cfa-32 ++ DW_CFA_advance_loc: 4 to 00000028 ++ DW_CFA_offset: r9 at cfa-24 ++ DW_CFA_advance_loc: 4 to 0000002c ++ DW_CFA_offset: r15 at cfa-16 ++ DW_CFA_advance_loc: 4 to 00000030 ++ DW_CFA_offset: r34 at cfa-8 ++ DW_CFA_advance_loc: 4 to 00000034 ++ DW_CFA_def_cfa_reg: r15 ++ DW_CFA_advance_loc: 36 to 00000058 ++ DW_CFA_def_cfa: r30 ofs 0 ++ DW_CFA_nop ++ +--- gas/testsuite/gas/cfi/cfi-alpha-3.s 2003-01-30 05:24:37.000000000 -0500 ++++ gas/testsuite/gas/cfi/cfi-alpha-3.s 2003-06-04 23:27:03.000000000 -0400 +@@ -0,0 +1,37 @@ ++ .file 1 "z.c" ++ .set noat ++ .set noreorder ++.text ++ .align 4 ++ .globl f ++ .type f,@function ++ .usepv f,no ++ .cfi_startproc ++f: ++ lda $30,-32($30) ++ .cfi_adjust_cfa_offset 32 ++ stq $26,0($30) ++ .cfi_offset $26, -32 ++ stq $9,8($30) ++ .cfi_offset $9, -24 ++ stq $15,16($30) ++ .cfi_offset $15, -16 ++ stt $f2,24($30) ++ .cfi_offset $f2, -8 ++ mov $30,$15 ++ .cfi_def_cfa_register $15 ++ ++ nop ++ nop ++ nop ++ ++ mov $15,$30 ++ ldq $26,0($30) ++ ldq $9,8($30) ++ ldt $f2,24($30) ++ ldq $15,16($30) ++ lda $30,32($30) ++ .cfi_def_cfa $30, 0 ++ ret $31,($26),1 ++ .size f, .-f ++ .cfi_endproc diff --git a/sys-devel/binutils/files/2.14/binutils-2.14.90.0.4-cfi3.patch b/sys-devel/binutils/files/2.14/binutils-2.14.90.0.4-cfi3.patch new file mode 100644 index 000000000000..b8881c7c83c6 --- /dev/null +++ b/sys-devel/binutils/files/2.14/binutils-2.14.90.0.4-cfi3.patch @@ -0,0 +1,509 @@ +2003-06-11 Richard Henderson <rth@redhat.com> + + * dw2gencfi.c (struct cfi_escape_data): New. + (cfi_add_CFA_nop): Remove. + (CFI_escape, dot_cfi_escape): New. + (dot_cfi): Remove nop. + (cfi_pseudo_table): Remove nop; add escape. + (output_cfi_insn): Likewise. + (select_cie_for_fde): Stop on escape. + * dw2gencfi.h (cfi_add_CFA_nop): Remove. + * read.c, read.h (do_parse_cons_expression): New. + +2003-06-07 Richard Henderson <rth@redhat.com> + + * dw2gencfi.c (struct cfa_save_data, cfa_save_stack): New. + (cfi_add_CFA_offset): Detect invalid offsets. + (cfi_add_CFA_remember_state): Save cur_cfa_offset. + (cfi_add_CFA_restore_state): Restore it. + (CFI_rel_offset): New. + (cfi_pseudo_table): Add it. + (dot_cfi): Handle it. + +testsuite/ +2003-06-11 Richard Henderson <rth@redhat.com> + + * gas/cfi/cfi-common-3.[ds]: New. + * gas/cfi/cfi.exp: Run it. + +2003-06-10 Alan Modra <amodra@bigpond.net.au> + + * lib/gas-defs.exp (proc is_elf_format): Copy from ld testsuite. + * gas/cfi/cfi.exp: Use here. Only run tests when ELF. + +2003-06-07 Richard Henderson <rth@redhat.com> + + * gas/cfi/cfi-common-1.d, gas/cfi/cfi-common-1.s: New. + * gas/cfi/cfi-common-2.d, gas/cfi/cfi-common-2.s: New. + * gas/cfi/cfi-diag-1.d, gas/cfi/cfi-diag-1.s: New. + * gas/cfi/cfi.exp: Run them. + +--- gas/dw2gencfi.c 5 Jun 2003 09:23:47 -0000 1.10 ++++ gas/dw2gencfi.c 11 Jun 2003 23:16:57 -0000 1.12 +@@ -68,6 +68,11 @@ struct cfi_insn_data + symbolS *lab1; + symbolS *lab2; + } ll; ++ ++ struct cfi_escape_data { ++ struct cfi_escape_data *next; ++ expressionS exp; ++ } *esc; + } u; + }; + +@@ -102,6 +107,14 @@ static struct fde_entry **last_fde_data + /* List of CIEs so that they could be reused. */ + static struct cie_entry *cie_root; + ++/* Stack of old CFI data, for save/restore. */ ++struct cfa_save_data ++{ ++ struct cfa_save_data *next; ++ offsetT cfa_offset; ++}; ++ ++static struct cfa_save_data *cfa_save_stack; + + /* Construct a new FDE structure and add it to the end of the fde list. */ + +@@ -231,7 +244,14 @@ cfi_add_advance_loc (symbolS *label) + void + cfi_add_CFA_offset (unsigned regno, offsetT offset) + { ++ unsigned int abs_data_align; ++ + cfi_add_CFA_insn_reg_offset (DW_CFA_offset, regno, offset); ++ ++ abs_data_align = (DWARF2_CIE_DATA_ALIGNMENT < 0 ++ ? -DWARF2_CIE_DATA_ALIGNMENT : DWARF2_CIE_DATA_ALIGNMENT); ++ if (offset % abs_data_align) ++ as_bad (_("register save offset not a multiple of %u"), abs_data_align); + } + + /* Add a DW_CFA_def_cfa record to the CFI data. */ +@@ -289,31 +309,45 @@ cfi_add_CFA_same_value (unsigned regno) + void + cfi_add_CFA_remember_state (void) + { ++ struct cfa_save_data *p; ++ + cfi_add_CFA_insn (DW_CFA_remember_state); ++ ++ p = xmalloc (sizeof (*p)); ++ p->cfa_offset = cur_cfa_offset; ++ p->next = cfa_save_stack; ++ cfa_save_stack = p; + } + + void + cfi_add_CFA_restore_state (void) + { ++ struct cfa_save_data *p; ++ + cfi_add_CFA_insn (DW_CFA_restore_state); +-} + +-void +-cfi_add_CFA_nop (void) +-{ +- cfi_add_CFA_insn (DW_CFA_nop); ++ p = cfa_save_stack; ++ if (p) ++ { ++ cur_cfa_offset = p->cfa_offset; ++ cfa_save_stack = p->next; ++ free (p); ++ } + } + + + /* Parse CFI assembler directives. */ + + static void dot_cfi (int); ++static void dot_cfi_escape (int); + static void dot_cfi_startproc (int); + static void dot_cfi_endproc (int); + + /* Fake CFI type; outside the byte range of any real CFI insn. */ + #define CFI_adjust_cfa_offset 0x100 + #define CFI_return_column 0x101 ++#define CFI_rel_offset 0x102 ++#define CFI_escape 0x103 + + const pseudo_typeS cfi_pseudo_table[] = + { +@@ -324,6 +358,7 @@ const pseudo_typeS cfi_pseudo_table[] = + { "cfi_def_cfa_offset", dot_cfi, DW_CFA_def_cfa_offset }, + { "cfi_adjust_cfa_offset", dot_cfi, CFI_adjust_cfa_offset }, + { "cfi_offset", dot_cfi, DW_CFA_offset }, ++ { "cfi_rel_offset", dot_cfi, CFI_rel_offset }, + { "cfi_register", dot_cfi, DW_CFA_register }, + { "cfi_return_column", dot_cfi, CFI_return_column }, + { "cfi_restore", dot_cfi, DW_CFA_restore }, +@@ -331,7 +366,7 @@ const pseudo_typeS cfi_pseudo_table[] = + { "cfi_same_value", dot_cfi, DW_CFA_same_value }, + { "cfi_remember_state", dot_cfi, DW_CFA_remember_state }, + { "cfi_restore_state", dot_cfi, DW_CFA_restore_state }, +- { "cfi_nop", dot_cfi, DW_CFA_nop }, ++ { "cfi_escape", dot_cfi_escape, 0 }, + { NULL, NULL, 0 } + }; + +@@ -422,6 +457,13 @@ dot_cfi (int arg) + cfi_add_CFA_offset (reg1, offset); + break; + ++ case CFI_rel_offset: ++ reg1 = cfi_parse_reg (); ++ cfi_parse_separator (); ++ offset = cfi_parse_const (); ++ cfi_add_CFA_offset (reg1, offset - cur_cfa_offset); ++ break; ++ + case DW_CFA_def_cfa: + reg1 = cfi_parse_reg (); + cfi_parse_separator (); +@@ -479,10 +521,6 @@ dot_cfi (int arg) + cfi_add_CFA_restore_state (); + break; + +- case DW_CFA_nop: +- cfi_add_CFA_nop (); +- break; +- + default: + abort (); + } +@@ -491,6 +529,39 @@ dot_cfi (int arg) + } + + static void ++dot_cfi_escape (int ignored ATTRIBUTE_UNUSED) ++{ ++ struct cfi_escape_data *head, **tail, *e; ++ struct cfi_insn_data *insn; ++ ++ if (!cur_fde_data) ++ { ++ as_bad (_("CFI instruction used without previous .cfi_startproc")); ++ return; ++ } ++ ++ /* If the last address was not at the current PC, advance to current. */ ++ if (symbol_get_frag (last_address) != frag_now ++ || S_GET_VALUE (last_address) != frag_now_fix ()) ++ cfi_add_advance_loc (symbol_temp_new_now ()); ++ ++ tail = &head; ++ do ++ { ++ e = xmalloc (sizeof (*e)); ++ do_parse_cons_expression (&e->exp, 1); ++ *tail = e; ++ tail = &e->next; ++ } ++ while (*input_line_pointer++ == ','); ++ *tail = NULL; ++ ++ insn = alloc_cfi_insn_data (); ++ insn->insn = CFI_escape; ++ insn->u.esc = head; ++} ++ ++static void + dot_cfi_startproc (int ignored ATTRIBUTE_UNUSED) + { + int simple = 0; +@@ -716,10 +787,17 @@ output_cfi_insn (struct cfi_insn_data *i + + case DW_CFA_remember_state: + case DW_CFA_restore_state: +- case DW_CFA_nop: + out_one (insn->insn); + break; + ++ case CFI_escape: ++ { ++ struct cfi_escape_data *e; ++ for (e = insn->u.esc; e ; e = e->next) ++ emit_expr (&e->exp, 1); ++ break; ++ } ++ + default: + abort (); + } +@@ -850,6 +928,10 @@ select_cie_for_fde (struct fde_entry *fd + if (i->u.i != j->u.i) + goto fail; + break; ++ ++ case CFI_escape: ++ /* Don't bother matching these for now. */ ++ goto fail; + + default: + abort (); +--- gas/dw2gencfi.h 5 Jun 2003 09:23:47 -0000 1.3 ++++ gas/dw2gencfi.h 11 Jun 2003 23:16:57 -0000 1.4 +@@ -48,6 +48,5 @@ extern void cfi_add_CFA_undefined (unsig + extern void cfi_add_CFA_same_value (unsigned); + extern void cfi_add_CFA_remember_state (void); + extern void cfi_add_CFA_restore_state (void); +-extern void cfi_add_CFA_nop (void); + + #endif /* DW2GENCFI_H */ +--- gas/read.c 2 Jun 2003 22:48:58 -0000 1.63 ++++ gas/read.c 11 Jun 2003 23:16:57 -0000 1.64 +@@ -3346,6 +3346,13 @@ parse_repeat_cons PARAMS ((expressionS * + #endif + #endif + ++void ++do_parse_cons_expression (expressionS *exp, int nbytes) ++{ ++ TC_PARSE_CONS_EXPRESSION (exp, nbytes); ++} ++ ++ + /* Worker to do .byte etc statements. + Clobbers input_line_pointer and checks end-of-line. */ + +--- gas/read.h 3 May 2003 06:10:59 -0000 1.17 ++++ gas/read.h 11 Jun 2003 23:16:57 -0000 1.18 +@@ -133,6 +133,7 @@ extern void stabs_generate_asm_func PARA + extern void stabs_generate_asm_endfunc PARAMS ((const char *, const char *)); + extern void do_repeat PARAMS((int,const char *,const char *)); + extern void end_repeat PARAMS((int)); ++extern void do_parse_cons_expression PARAMS ((expressionS *, int)); + + extern void generate_lineno_debug PARAMS ((void)); + +--- gas/testsuite/gas/cfi/cfi.exp 5 Jun 2003 03:27:03 -0000 1.4 ++++ gas/testsuite/gas/cfi/cfi.exp 11 Jun 2003 23:16:58 -0000 1.7 +@@ -1,21 +1,37 @@ ++# ??? This probably shouldn't be replicated here... ++proc run_list_test { name opts } { ++ global srcdir subdir ++ set testname "cfi $name" ++ set file $srcdir/$subdir/$name ++ gas_run ${name}.s $opts ">&dump.out" ++ if { [regexp_diff "dump.out" "${file}.l"] } then { ++ fail $testname ++ verbose "output is [file_contents "dump.out"]" 2 ++ return ++ } ++ pass $testname ++} ++ ++if ![is_elf_format] then { ++ return ++} ++ + if [istarget "x86_64-*"] then { + run_dump_test "cfi-x86_64" +-} + +-if [istarget "i?86-*"] then { ++} elseif [istarget "i?86-*"] then { + run_dump_test "cfi-i386" +-} + +-if { [istarget alpha*-*-*] } then { ++} elseif { [istarget alpha*-*-*] } then { ++ run_dump_test "cfi-alpha-1" ++ run_dump_test "cfi-alpha-2" ++ run_dump_test "cfi-alpha-3" + +- set elf [expr [istarget *-*-elf*] \ +- || [istarget *-*-linux*] \ +- || [istarget *-*-freebsd*] \ +- || [istarget *-*-netbsd*] ] +- +- if $elf { +- run_dump_test "cfi-alpha-1" +- run_dump_test "cfi-alpha-2" +- run_dump_test "cfi-alpha-3" +- } ++} else { ++ return + } ++ ++run_list_test "cfi-diag-1" "" ++run_dump_test "cfi-common-1" ++run_dump_test "cfi-common-2" ++run_dump_test "cfi-common-3" +--- gas/testsuite/lib/gas-defs.exp 16 May 2003 16:30:25 -0000 1.12 ++++ gas/testsuite/lib/gas-defs.exp 10 Jun 2003 13:31:59 -0000 1.13 +@@ -182,6 +182,43 @@ proc gas_init { args } { + return + } + ++# ++# is_elf_format ++# true if the object format is known to be ELF ++# ++proc is_elf_format {} { ++ if { ![istarget *-*-sysv4*] \ ++ && ![istarget *-*-unixware*] \ ++ && ![istarget *-*-elf*] \ ++ && ![istarget *-*-eabi*] \ ++ && ![istarget hppa*64*-*-hpux*] \ ++ && ![istarget *-*-linux*] \ ++ && ![istarget *-*-irix5*] \ ++ && ![istarget *-*-irix6*] \ ++ && ![istarget *-*-netbsd*] \ ++ && ![istarget *-*-solaris2*] } { ++ return 0 ++ } ++ ++ if { [istarget *-*-linux*aout*] \ ++ || [istarget *-*-linux*oldld*] } { ++ return 0 ++ } ++ ++ if { ![istarget *-*-netbsdelf*] \ ++ && ([istarget *-*-netbsd*aout*] \ ++ || [istarget *-*-netbsdpe*] \ ++ || [istarget arm*-*-netbsd*] \ ++ || [istarget sparc-*-netbsd*] \ ++ || [istarget i*86-*-netbsd*] \ ++ || [istarget m68*-*-netbsd*] \ ++ || [istarget vax-*-netbsd*] \ ++ || [istarget ns32k-*-netbsd*]) } { ++ return 0 ++ } ++ return 1 ++} ++ + + # run_dump_test FILE (optional:) EXTRA_OPTIONS + # +--- gas/testsuite/gas/cfi/cfi-common-1.d 2003-01-30 05:24:37.000000000 -0500 ++++ gas/testsuite/gas/cfi/cfi-common-1.d 2003-06-07 23:59:44.000000000 -0400 +@@ -0,0 +1,24 @@ ++#readelf: -wf ++#name: CFI common 1 ++The section .eh_frame contains: ++ ++00000000 00000010 00000000 CIE ++ Version: 1 ++ Augmentation: "zR" ++ Code alignment factor: .* ++ Data alignment factor: .* ++ Return address column: .* ++ Augmentation data: 1b ++ ++ DW_CFA_nop ++ DW_CFA_nop ++ DW_CFA_nop ++ ++00000014 00000018 00000018 FDE cie=00000000 pc=.* ++ DW_CFA_advance_loc: 4 to .* ++ DW_CFA_def_cfa: r0 ofs 16 ++ DW_CFA_offset: r1 at cfa-8 ++ DW_CFA_advance_loc: 4 to .* ++ DW_CFA_def_cfa_offset: 32 ++ DW_CFA_offset: r2 at cfa-24 ++ +--- gas/testsuite/gas/cfi/cfi-common-1.s 2003-01-30 05:24:37.000000000 -0500 ++++ gas/testsuite/gas/cfi/cfi-common-1.s 2003-06-07 23:59:44.000000000 -0400 +@@ -0,0 +1,8 @@ ++ .cfi_startproc simple ++ .long 0 ++ .cfi_def_cfa 0, 16 ++ .cfi_rel_offset 1, 8 ++ .long 0 ++ .cfi_adjust_cfa_offset 16 ++ .cfi_rel_offset 2, 8 ++ .cfi_endproc +--- gas/testsuite/gas/cfi/cfi-common-2.d 2003-01-30 05:24:37.000000000 -0500 ++++ gas/testsuite/gas/cfi/cfi-common-2.d 2003-06-07 23:59:44.000000000 -0400 +@@ -0,0 +1,29 @@ ++#readelf: -wf ++#name: CFI common 2 ++The section .eh_frame contains: ++ ++00000000 00000010 00000000 CIE ++ Version: 1 ++ Augmentation: "zR" ++ Code alignment factor: .* ++ Data alignment factor: .* ++ Return address column: .* ++ Augmentation data: 1b ++ ++ DW_CFA_nop ++ DW_CFA_nop ++ DW_CFA_nop ++ ++00000014 0000001c 00000018 FDE cie=00000000 pc=.* ++ DW_CFA_advance_loc: 4 to .* ++ DW_CFA_def_cfa: r0 ofs 16 ++ DW_CFA_advance_loc: 4 to .* ++ DW_CFA_remember_state ++ DW_CFA_advance_loc: 4 to .* ++ DW_CFA_def_cfa_offset: 0 ++ DW_CFA_advance_loc: 4 to .* ++ DW_CFA_restore_state ++ DW_CFA_advance_loc: 4 to .* ++ DW_CFA_def_cfa_offset: 0 ++ DW_CFA_nop ++ +--- gas/testsuite/gas/cfi/cfi-common-2.s 2003-01-30 05:24:37.000000000 -0500 ++++ gas/testsuite/gas/cfi/cfi-common-2.s 2003-06-07 23:59:44.000000000 -0400 +@@ -0,0 +1,12 @@ ++ .cfi_startproc simple ++ .long 0 ++ .cfi_def_cfa 0, 16 ++ .long 0 ++ .cfi_remember_state ++ .long 0 ++ .cfi_adjust_cfa_offset -16 ++ .long 0 ++ .cfi_restore_state ++ .long 0 ++ .cfi_adjust_cfa_offset -16 ++ .cfi_endproc +--- gas/testsuite/gas/cfi/cfi-common-3.d 2003-01-30 05:24:37.000000000 -0500 ++++ gas/testsuite/gas/cfi/cfi-common-3.d 2003-06-11 19:16:58.000000000 -0400 +@@ -0,0 +1,21 @@ ++#readelf: -wf ++#name: CFI common 2 ++The section .eh_frame contains: ++ ++00000000 00000010 00000000 CIE ++ Version: 1 ++ Augmentation: "zR" ++ Code alignment factor: .* ++ Data alignment factor: .* ++ Return address column: .* ++ Augmentation data: 1b ++ ++ DW_CFA_nop ++ DW_CFA_nop ++ DW_CFA_nop ++ ++00000014 00000010 00000018 FDE cie=00000000 pc=.* ++ DW_CFA_advance_loc: 4 to .* ++ DW_CFA_remember_state ++ DW_CFA_restore_state ++ +--- gas/testsuite/gas/cfi/cfi-common-3.s 2003-01-30 05:24:37.000000000 -0500 ++++ gas/testsuite/gas/cfi/cfi-common-3.s 2003-06-11 19:16:58.000000000 -0400 +@@ -0,0 +1,4 @@ ++ .cfi_startproc simple ++ .long 0 ++ .cfi_escape 10, 11 ++ .cfi_endproc +--- gas/testsuite/gas/cfi/cfi-diag-1.l 2003-01-30 05:24:37.000000000 -0500 ++++ gas/testsuite/gas/cfi/cfi-diag-1.l 2003-06-07 23:59:44.000000000 -0400 +@@ -0,0 +1,2 @@ ++.*: Assembler messages: ++.*:2: Error: register save offset not a multiple of .* +--- gas/testsuite/gas/cfi/cfi-diag-1.s 2003-01-30 05:24:37.000000000 -0500 ++++ gas/testsuite/gas/cfi/cfi-diag-1.s 2003-06-07 23:59:44.000000000 -0400 +@@ -0,0 +1,3 @@ ++ .cfi_startproc ++ .cfi_offset 0, 1 ++ .cfi_endproc diff --git a/sys-devel/binutils/files/2.14/binutils-2.14.90.0.4-cfi4.patch b/sys-devel/binutils/files/2.14/binutils-2.14.90.0.4-cfi4.patch new file mode 100644 index 000000000000..153703986c87 --- /dev/null +++ b/sys-devel/binutils/files/2.14/binutils-2.14.90.0.4-cfi4.patch @@ -0,0 +1,384 @@ +2003-06-18 Jakub Jelinek <jakub@redhat.com> + + * dw2gencfi.c (EH_FRAME_ALIGNMENT): Define if not defined. + (output_cie): Don't pad. + (output_fde): Add align argument. Pad to align if not 0. + (cfi_finish): Set .eh_frame alignment to EH_FRAME_ALIGNMENT. + Pad just last FDE to EH_FRAME_ALIGNMENT. + + * gas/cfi/cfi-i386.d: Regenerated. + * gas/cfi/cfi-common-1.d: Regenerated. + * gas/cfi/cfi-common-2.d: Regenerated. + * gas/cfi/cfi-common-3.d: Regenerated. + * gas/cfi/cfi-x86_64.d: Regenerated. + * gas/cfi/cfi-alpha-1.d: Regenerated. + * gas/cfi/cfi-alpha-2.d: Regenerated. + * gas/cfi/cfi-alpha-3.d: Regenerated. + +--- gas/dw2gencfi.c.jj 2003-06-17 03:59:16.000000000 -0400 ++++ gas/dw2gencfi.c 2003-06-18 07:25:06.000000000 -0400 +@@ -41,6 +41,14 @@ + # endif + #endif + ++#ifndef EH_FRAME_ALIGNMENT ++# ifdef BFD_ASSEMBLER ++# define EH_FRAME_ALIGNMENT (bfd_get_arch_size (stdoutput) == 64 ? 3 : 2) ++# else ++# define EH_FRAME_ALIGNMENT 2 ++# endif ++#endif ++ + #ifndef tc_cfi_frame_initial_instructions + # define tc_cfi_frame_initial_instructions() ((void)0) + #endif +@@ -836,13 +844,12 @@ output_cie (struct cie_entry *cie) + for (i = cie->first; i != cie->last; i = i->next) + output_cfi_insn (i); + +- frag_align (2, 0, 0); + symbol_set_value_now (end_address); + } + + static void + output_fde (struct fde_entry *fde, struct cie_entry *cie, +- struct cfi_insn_data *first) ++ struct cfi_insn_data *first, int align) + { + symbolS *after_size_address, *end_address; + expressionS exp; +@@ -874,7 +881,8 @@ output_fde (struct fde_entry *fde, struc + for (; first; first = first->next) + output_cfi_insn (first); + +- frag_align (2, 0, 0); ++ if (align) ++ frag_align (align, 0, 0); + symbol_set_value_now (end_address); + } + +@@ -990,7 +998,7 @@ cfi_finish (void) + SEC_ALLOC | SEC_LOAD | SEC_DATA | SEC_READONLY); + #endif + subseg_set (cfi_seg, 0); +- record_alignment (cfi_seg, 2); ++ record_alignment (cfi_seg, EH_FRAME_ALIGNMENT); + + /* Make sure check_eh_frame doesn't do anything with our output. */ + save_flag_traditional_format = flag_traditional_format; +@@ -1002,7 +1010,7 @@ cfi_finish (void) + struct cie_entry *cie; + + cie = select_cie_for_fde (fde, &first); +- output_fde (fde, cie, first); ++ output_fde (fde, cie, first, fde->next == NULL ? EH_FRAME_ALIGNMENT : 0); + } + + flag_traditional_format = save_flag_traditional_format; +--- gas/testsuite/gas/cfi/cfi-i386.d.jj 2003-05-28 02:56:00.000000000 -0400 ++++ gas/testsuite/gas/cfi/cfi-i386.d 2003-06-18 12:04:17.000000000 -0400 +@@ -2,7 +2,7 @@ + #name: CFI on i386 + The section .eh_frame contains: + +-00000000 00000014 00000000 CIE ++00000000 00000012 00000000 CIE + Version: 1 + Augmentation: "zR" + Code alignment factor: 1 +@@ -12,37 +12,29 @@ The section .eh_frame contains: + + DW_CFA_def_cfa: r4 ofs 4 + DW_CFA_offset: r8 at cfa-4 +- DW_CFA_nop +- DW_CFA_nop + +-00000018 00000014 0000001c FDE cie=00000000 pc=00000020..00000032 +- DW_CFA_advance_loc: 6 to 00000026 ++00000016 00000014 0000001a FDE cie=00000000 pc=0000001e..00000030 ++ DW_CFA_advance_loc: 6 to 00000024 + DW_CFA_def_cfa_offset: 4664 +- DW_CFA_advance_loc: 11 to 00000031 ++ DW_CFA_advance_loc: 11 to 0000002f + DW_CFA_def_cfa_offset: 4 + +-00000030 00000018 00000034 FDE cie=00000000 pc=0000004a..00000057 +- DW_CFA_advance_loc: 1 to 0000004b ++0000002e 00000018 00000032 FDE cie=00000000 pc=00000048..00000055 ++ DW_CFA_advance_loc: 1 to 00000049 + DW_CFA_def_cfa_offset: 8 + DW_CFA_offset: r5 at cfa-8 +- DW_CFA_advance_loc: 2 to 0000004d ++ DW_CFA_advance_loc: 2 to 0000004b + DW_CFA_def_cfa_reg: r5 +- DW_CFA_advance_loc: 9 to 00000056 ++ DW_CFA_advance_loc: 9 to 00000054 + DW_CFA_def_cfa_reg: r4 + +-0000004c 00000014 00000050 FDE cie=00000000 pc=00000073..00000083 +- DW_CFA_advance_loc: 2 to 00000075 ++0000004a 00000014 0000004e FDE cie=00000000 pc=00000071..00000081 ++ DW_CFA_advance_loc: 2 to 00000073 + DW_CFA_def_cfa_reg: r3 +- DW_CFA_advance_loc: 13 to 00000082 ++ DW_CFA_advance_loc: 13 to 00000080 + DW_CFA_def_cfa: r4 ofs 4 + +-00000064 00000010 00000068 FDE cie=00000000 pc=0000009b..000000a1 +- DW_CFA_nop +- DW_CFA_nop +- DW_CFA_nop +- +-00000078 00000010 0000007c FDE cie=00000000 pc=000000b5..000000c4 +- DW_CFA_nop +- DW_CFA_nop +- DW_CFA_nop ++00000062 0000000d 00000066 FDE cie=00000000 pc=00000099..0000009f ++ ++00000073 0000000d 00000077 FDE cie=00000000 pc=000000b0..000000bf + +--- gas/testsuite/gas/cfi/cfi-common-1.d.jj 2003-06-07 23:59:44.000000000 -0400 ++++ gas/testsuite/gas/cfi/cfi-common-1.d 2003-06-18 12:13:51.000000000 -0400 +@@ -2,7 +2,7 @@ + #name: CFI common 1 + The section .eh_frame contains: + +-00000000 00000010 00000000 CIE ++00000000 0000000d 00000000 CIE + Version: 1 + Augmentation: "zR" + Code alignment factor: .* +@@ -10,15 +10,14 @@ The section .eh_frame contains: + Return address column: .* + Augmentation data: 1b + +- DW_CFA_nop +- DW_CFA_nop +- DW_CFA_nop + +-00000014 00000018 00000018 FDE cie=00000000 pc=.* ++00000011 0000001b 00000015 FDE cie=00000000 pc=.* + DW_CFA_advance_loc: 4 to .* + DW_CFA_def_cfa: r0 ofs 16 + DW_CFA_offset: r1 at cfa-8 + DW_CFA_advance_loc: 4 to .* + DW_CFA_def_cfa_offset: 32 + DW_CFA_offset: r2 at cfa-24 +- ++ DW_CFA_nop ++ DW_CFA_nop ++ DW_CFA_nop +--- gas/testsuite/gas/cfi/cfi-common-2.d.jj 2003-06-07 23:59:44.000000000 -0400 ++++ gas/testsuite/gas/cfi/cfi-common-2.d 2003-06-18 12:16:12.000000000 -0400 +@@ -2,7 +2,7 @@ + #name: CFI common 2 + The section .eh_frame contains: + +-00000000 00000010 00000000 CIE ++00000000 0000000d 00000000 CIE + Version: 1 + Augmentation: "zR" + Code alignment factor: .* +@@ -10,11 +10,8 @@ The section .eh_frame contains: + Return address column: .* + Augmentation data: 1b + +- DW_CFA_nop +- DW_CFA_nop +- DW_CFA_nop + +-00000014 0000001c 00000018 FDE cie=00000000 pc=.* ++00000011 0000001[bf] 00000015 FDE cie=00000000 pc=.* + DW_CFA_advance_loc: 4 to .* + DW_CFA_def_cfa: r0 ofs 16 + DW_CFA_advance_loc: 4 to .* +@@ -25,5 +22,5 @@ The section .eh_frame contains: + DW_CFA_restore_state + DW_CFA_advance_loc: 4 to .* + DW_CFA_def_cfa_offset: 0 +- DW_CFA_nop +- ++# 64-bit arches will have here 4 times DW_CFA_nop ++#... +--- gas/testsuite/gas/cfi/cfi-x86_64.d.jj 2003-05-28 02:56:00.000000000 -0400 ++++ gas/testsuite/gas/cfi/cfi-x86_64.d 2003-06-18 12:30:09.000000000 -0400 +@@ -2,7 +2,7 @@ + #name: CFI on x86-64 + The section .eh_frame contains: + +-00000000 00000014 00000000 CIE ++00000000 00000012 00000000 CIE + Version: 1 + Augmentation: "zR" + Code alignment factor: 1 +@@ -12,40 +12,32 @@ The section .eh_frame contains: + + DW_CFA_def_cfa: r7 ofs 8 + DW_CFA_offset: r16 at cfa-8 +- DW_CFA_nop +- DW_CFA_nop + +-00000018 00000014 0000001c FDE cie=00000000 pc=00000020..00000034 +- DW_CFA_advance_loc: 7 to 00000027 ++00000016 00000014 0000001a FDE cie=00000000 pc=0000001e..00000032 ++ DW_CFA_advance_loc: 7 to 00000025 + DW_CFA_def_cfa_offset: 4668 +- DW_CFA_advance_loc: 12 to 00000033 ++ DW_CFA_advance_loc: 12 to 00000031 + DW_CFA_def_cfa_offset: 8 + +-00000030 0000001c 00000034 FDE cie=00000000 pc=00000038..00000047 +- DW_CFA_advance_loc: 1 to 00000039 ++0000002e 00000019 00000032 FDE cie=00000000 pc=00000036..00000045 ++ DW_CFA_advance_loc: 1 to 00000037 + DW_CFA_def_cfa_offset: 16 + DW_CFA_offset: r6 at cfa-16 +- DW_CFA_advance_loc: 3 to 0000003c ++ DW_CFA_advance_loc: 3 to 0000003a + DW_CFA_def_cfa_reg: r6 +- DW_CFA_advance_loc: 10 to 00000046 ++ DW_CFA_advance_loc: 10 to 00000044 + DW_CFA_def_cfa: r7 ofs 8 +- DW_CFA_nop +- DW_CFA_nop +- DW_CFA_nop + +-00000050 00000014 00000054 FDE cie=00000000 pc=00000058..0000006b +- DW_CFA_advance_loc: 3 to 0000005b ++0000004b 00000013 0000004f FDE cie=00000000 pc=00000053..00000066 ++ DW_CFA_advance_loc: 3 to 00000056 + DW_CFA_def_cfa_reg: r12 +- DW_CFA_advance_loc: 15 to 0000006a ++ DW_CFA_advance_loc: 15 to 00000065 + DW_CFA_def_cfa_reg: r7 +- DW_CFA_nop + +-00000068 00000010 0000006c FDE cie=00000000 pc=00000070..00000076 +- DW_CFA_nop +- DW_CFA_nop +- DW_CFA_nop ++00000062 0000000d 00000066 FDE cie=00000000 pc=0000006a..00000070 + +-0000007c 00000010 00000080 FDE cie=00000000 pc=00000084..00000096 ++00000073 00000011 00000077 FDE cie=00000000 pc=0000007b..0000008d ++ DW_CFA_nop + DW_CFA_nop + DW_CFA_nop + DW_CFA_nop +--- gas/testsuite/gas/cfi/cfi-common-3.d.jj 2003-06-11 19:16:58.000000000 -0400 ++++ gas/testsuite/gas/cfi/cfi-common-3.d 2003-06-18 12:18:06.000000000 -0400 +@@ -1,8 +1,8 @@ + #readelf: -wf +-#name: CFI common 2 ++#name: CFI common 3 + The section .eh_frame contains: + +-00000000 00000010 00000000 CIE ++00000000 0000000d 00000000 CIE + Version: 1 + Augmentation: "zR" + Code alignment factor: .* +@@ -10,12 +10,11 @@ The section .eh_frame contains: + Return address column: .* + Augmentation data: 1b + +- DW_CFA_nop +- DW_CFA_nop +- DW_CFA_nop + +-00000014 00000010 00000018 FDE cie=00000000 pc=.* ++00000011 00000013 00000015 FDE cie=00000000 pc=.* + DW_CFA_advance_loc: 4 to .* + DW_CFA_remember_state + DW_CFA_restore_state +- ++ DW_CFA_nop ++ DW_CFA_nop ++ DW_CFA_nop +--- gas/testsuite/gas/cfi/cfi-alpha-1.d.jj 2003-05-29 23:01:12.000000000 -0400 ++++ gas/testsuite/gas/cfi/cfi-alpha-1.d 2003-06-18 12:38:36.000000000 -0400 +@@ -2,7 +2,7 @@ + #name: CFI on alpha + The section .eh_frame contains: + +-00000000 00000010 00000000 CIE ++00000000 0000000f 00000000 CIE + Version: 1 + Augmentation: "zR" + Code alignment factor: 4 +@@ -11,16 +11,12 @@ The section .eh_frame contains: + Augmentation data: 1b + + DW_CFA_def_cfa_reg: r30 +- DW_CFA_nop + +-00000014 0000001c 00000018 FDE cie=00000000 pc=0000001c..00000050 +- DW_CFA_advance_loc: 24 to 00000034 ++00000013 00000019 00000017 FDE cie=00000000 pc=0000001b..0000004f ++ DW_CFA_advance_loc: 24 to 00000033 + DW_CFA_def_cfa: r15 ofs 32 + DW_CFA_offset: r26 at cfa-32 + DW_CFA_offset: r9 at cfa-24 + DW_CFA_offset: r15 at cfa-16 + DW_CFA_offset: r34 at cfa-8 +- DW_CFA_nop +- DW_CFA_nop +- DW_CFA_nop + +--- gas/testsuite/gas/cfi/cfi-alpha-2.d.jj 2003-05-31 15:36:45.000000000 -0400 ++++ gas/testsuite/gas/cfi/cfi-alpha-2.d 2003-06-18 12:41:56.000000000 -0400 +@@ -5,5 +5,5 @@ + + RELOCATION RECORDS FOR \[\.eh_frame\]: + OFFSET TYPE VALUE +-0*000001c SREL32 \.text +-0*0000030 SREL32 \.text\+0x0*0000004 ++0*000001b SREL32 \.text ++0*000002c SREL32 \.text\+0x0*0000004 +--- gas/testsuite/gas/cfi/cfi-alpha-3.d.jj 2003-06-04 23:27:03.000000000 -0400 ++++ gas/testsuite/gas/cfi/cfi-alpha-3.d 2003-06-18 12:42:52.000000000 -0400 +@@ -2,7 +2,7 @@ + #name: CFI on alpha, 3 + The section .eh_frame contains: + +-00000000 00000010 00000000 CIE ++00000000 0000000f 00000000 CIE + Version: 1 + Augmentation: "zR" + Code alignment factor: 4 +@@ -11,22 +11,26 @@ The section .eh_frame contains: + Augmentation data: 1b + + DW_CFA_def_cfa_reg: r30 +- DW_CFA_nop + +-00000014 00000024 00000018 FDE cie=00000000 pc=0000001c..0000005c +- DW_CFA_advance_loc: 4 to 00000020 ++00000013 00000029 00000017 FDE cie=00000000 pc=0000001b..0000005b ++ DW_CFA_advance_loc: 4 to 0000001f + DW_CFA_def_cfa_offset: 32 +- DW_CFA_advance_loc: 4 to 00000024 ++ DW_CFA_advance_loc: 4 to 00000023 + DW_CFA_offset: r26 at cfa-32 +- DW_CFA_advance_loc: 4 to 00000028 ++ DW_CFA_advance_loc: 4 to 00000027 + DW_CFA_offset: r9 at cfa-24 +- DW_CFA_advance_loc: 4 to 0000002c ++ DW_CFA_advance_loc: 4 to 0000002b + DW_CFA_offset: r15 at cfa-16 +- DW_CFA_advance_loc: 4 to 00000030 ++ DW_CFA_advance_loc: 4 to 0000002f + DW_CFA_offset: r34 at cfa-8 +- DW_CFA_advance_loc: 4 to 00000034 ++ DW_CFA_advance_loc: 4 to 00000033 + DW_CFA_def_cfa_reg: r15 +- DW_CFA_advance_loc: 36 to 00000058 ++ DW_CFA_advance_loc: 36 to 00000057 + DW_CFA_def_cfa: r30 ofs 0 + DW_CFA_nop ++ DW_CFA_nop ++ DW_CFA_nop ++ DW_CFA_nop ++ DW_CFA_nop ++ DW_CFA_nop + diff --git a/sys-devel/binutils/files/2.14/binutils-2.14.90.0.4-eh-frame-ro.patch b/sys-devel/binutils/files/2.14/binutils-2.14.90.0.4-eh-frame-ro.patch new file mode 100644 index 000000000000..83b947df1b06 --- /dev/null +++ b/sys-devel/binutils/files/2.14/binutils-2.14.90.0.4-eh-frame-ro.patch @@ -0,0 +1,475 @@ +2002-11-22 Jakub Jelinek <jakub@redhat.com> + + * ldgram.y (sect_constraint): New. + (ONLY_IF_RO, ONLY_IF_RW): New tokens. + (section): Add sect_constraint. Pass additional argument + to lang_enter_output_section_statement. + * mri.c (mri_draw_tree): Pass additional argument to + lang_enter_output_section_statement. + * emultempl/pe.em (place_orphan): Likewise. + (output_prev_sec_find): Disregard output section statements with + constraint == -1. + * emultempl/mmo.em (output_prev_sec_find): Likewise. + (mmo_place_orphan): Pass additional argument to + lang_enter_output_section_statement. + * emultempl/elf32.em (output_prev_sec_find): Disregard output section + statements with constraint == -1. + (place_orphan): Pass additional argument to + lang_enter_output_section_statement. + * ldlang.c (lang_enter_overlay_section): Likewise. + (lang_output_section_find_1): New. + (lang_output_section_find): Use it. + (lang_output_section_statement_lookup_1): New. + (lang_output_section_statement_lookup): Use it. + (check_section_callback, check_input_sections): New. + (map_input_to_output_sections): Check if all input sections + are readonly if ONLY_IF_RO or ONLY_IF_RW was seen. + (strip_excluded_output_sections): Disregard output section statements + with constraint == -1. + (lang_record_phdrs): Likewise. + (lang_enter_output_section_statement): Add constraint argument. + Use lang_output_section_statement_lookup_1. + * ldlang.h (lang_output_section_statement_type): Add constraint + and all_input_readonly fields. + (lang_enter_output_section_statement): Adjust prototype. + * ldlex.l (ONLY_IF_RO, ONLY_IF_RW): New tokens. + * scripttempl/elf.sc (.eh_frame, .gcc_except_table): Move into text + segment if all input sections are readonly. + +--- ld/emultempl/mmo.em.jj Mon Dec 16 15:22:53 2002 ++++ ld/emultempl/mmo.em Mon May 19 06:31:40 2003 +@@ -56,6 +56,8 @@ output_prev_sec_find (os) + u = lookup->next) + { + lookup = &u->output_section_statement; ++ if (lookup->constraint == -1) ++ continue; + if (lookup == os) + break; + if (lookup->bfd_section != NULL +@@ -141,7 +143,7 @@ mmo_place_orphan (file, s) + (bfd_vma) 0, + (etree_type *) NULL, + (etree_type *) NULL, +- (etree_type *) NULL); ++ (etree_type *) NULL, 0); + + lang_add_section (&os->children, s, os, file); + +--- ld/emultempl/pe.em.jj Mon May 5 17:46:50 2003 ++++ ld/emultempl/pe.em Mon May 19 06:31:40 2003 +@@ -1511,6 +1511,8 @@ output_prev_sec_find (os) + u = lookup->next) + { + lookup = &u->output_section_statement; ++ if (lookup->constraint == -1) ++ continue; + if (lookup == os) + return s; + +@@ -1677,7 +1679,7 @@ gld_${EMULATION_NAME}_place_orphan (file + (bfd_vma) 0, + (etree_type *) NULL, + (etree_type *) NULL, +- (etree_type *) NULL); ++ (etree_type *) NULL, 0); + + lang_add_section (&add_child, s, os, file); + +--- ld/emultempl/elf32.em.jj Thu May 15 16:42:25 2003 ++++ ld/emultempl/elf32.em Mon May 19 06:31:40 2003 +@@ -1056,7 +1056,8 @@ output_rel_find (sec) + for (u = lang_output_section_statement.head; u; u = lookup->next) + { + lookup = &u->output_section_statement; +- if (strncmp (".rel", lookup->name, 4) == 0) ++ if (lookup->constraint != -1 ++ && strncmp (".rel", lookup->name, 4) == 0) + { + /* Don't place after .rel.plt as doing so results in wrong + dynamic tags. Also, place allocated reloc sections before +@@ -1296,7 +1297,7 @@ gld${EMULATION_NAME}_place_orphan (file, + (bfd_vma) 0, + (etree_type *) NULL, + (etree_type *) NULL, +- load_base); ++ load_base, 0); + + lang_add_section (&os->children, s, os, file); + +--- ld/scripttempl/elf.sc.jj Mon May 5 17:46:50 2003 ++++ ld/scripttempl/elf.sc Mon May 19 06:31:40 2003 +@@ -280,6 +280,8 @@ cat <<EOF + ${CREATE_SHLIB-${SBSS2}} + ${OTHER_READONLY_SECTIONS} + .eh_frame_hdr : { *(.eh_frame_hdr) } ++ .eh_frame ${RELOCATING-0} : ONLY_IF_RO { KEEP (*(.eh_frame)) } ++ .gcc_except_table ${RELOCATING-0} : ONLY_IF_RO { *(.gcc_except_table) } + + /* Adjust the address for the data segment. We want to adjust up to + the same address within the page on the next page up. */ +@@ -312,8 +314,8 @@ cat <<EOF + .data1 ${RELOCATING-0} : { *(.data1) } + .tdata ${RELOCATING-0} : { *(.tdata${RELOCATING+ .tdata.* .gnu.linkonce.td.*}) } + .tbss ${RELOCATING-0} : { *(.tbss${RELOCATING+ .tbss.* .gnu.linkonce.tb.*})${RELOCATING+ *(.tcommon)} } +- .eh_frame ${RELOCATING-0} : { KEEP (*(.eh_frame)) } +- .gcc_except_table ${RELOCATING-0} : { *(.gcc_except_table) } ++ .eh_frame ${RELOCATING-0} : ONLY_IF_RW { KEEP (*(.eh_frame)) } ++ .gcc_except_table ${RELOCATING-0} : ONLY_IF_RW { *(.gcc_except_table) } + ${WRITABLE_RODATA+${RODATA}} + ${OTHER_READWRITE_SECTIONS} + ${TEXT_DYNAMIC-${DYNAMIC}} +--- ld/ldgram.y.jj Mon May 5 17:46:49 2003 ++++ ld/ldgram.y Mon May 19 06:34:38 2003 +@@ -143,14 +143,14 @@ static int error_index; + %token ORIGIN FILL + %token LENGTH CREATE_OBJECT_SYMBOLS INPUT GROUP OUTPUT CONSTRUCTORS + %token ALIGNMOD AT PROVIDE +-%type <token> assign_op atype attributes_opt ++%type <token> assign_op atype attributes_opt sect_constraint + %type <name> filename + %token CHIP LIST SECT ABSOLUTE LOAD NEWLINE ENDWORD ORDER NAMEWORD ASSERT_K + %token FORMAT PUBLIC DEFSYMEND BASE ALIAS TRUNCATE REL + %token INPUT_SCRIPT INPUT_MRI_SCRIPT INPUT_DEFSYM CASE EXTERN START + %token <name> VERS_TAG VERS_IDENTIFIER + %token GLOBAL LOCAL VERSIONK INPUT_VERSION_SCRIPT +-%token KEEP ++%token KEEP ONLY_IF_RO ONLY_IF_RW + %token EXCLUDE_FILE + %type <versyms> vers_defns + %type <versnode> vers_tag +@@ -828,21 +828,28 @@ opt_at: + | { $$ = 0; } + ; + ++sect_constraint: ++ ONLY_IF_RO { $$ = ONLY_IF_RO; } ++ | ONLY_IF_RW { $$ = ONLY_IF_RW; } ++ | { $$ = 0; } ++ ; ++ + section: NAME { ldlex_expression(); } + opt_exp_with_type + opt_at { ldlex_popstate (); ldlex_script (); } ++ sect_constraint + '{' + { + lang_enter_output_section_statement($1, $3, + sectype, +- 0, 0, 0, $4); ++ 0, 0, 0, $4, $6); + } + statement_list_opt + '}' { ldlex_popstate (); ldlex_expression (); } + memspec_opt memspec_at_opt phdr_opt fill_opt + { + ldlex_popstate (); +- lang_leave_output_section_statement ($14, $11, $13, $12); ++ lang_leave_output_section_statement ($15, $12, $14, $13); + } + opt_comma + {} +--- ld/mri.c.jj Tue Jan 21 13:21:34 2003 ++++ ld/mri.c Mon May 19 06:31:40 2003 +@@ -237,7 +237,7 @@ mri_draw_tree () + lang_enter_output_section_statement (p->name, base, + p->ok_to_load ? 0 : noload_section, + 1, align, subalign, +- (etree_type *) NULL); ++ (etree_type *) NULL, 0); + base = 0; + tmp = (struct wildcard_list *) xmalloc (sizeof *tmp); + tmp->next = NULL; +--- ld/ldlang.h.jj Wed Mar 19 12:19:16 2003 ++++ ld/ldlang.h Mon May 19 06:31:40 2003 +@@ -132,6 +132,8 @@ typedef struct lang_output_section_state + + int subsection_alignment; /* alignment of components */ + int section_alignment; /* alignment of start of section */ ++ int constraint; ++ bfd_boolean all_input_readonly; + + union etree_union *load_base; + +@@ -394,7 +396,7 @@ extern lang_output_section_statement_typ + bfd_vma block_value, + etree_type *align, + etree_type *subalign, +- etree_type *)); ++ etree_type *, int)); + extern void lang_final + PARAMS ((void)); + extern void lang_process +--- ld/ldlang.c.jj Thu May 15 16:42:25 2003 ++++ ld/ldlang.c Mon May 19 06:31:40 2003 +@@ -72,6 +72,10 @@ static lang_input_statement_type *new_af + bfd_boolean)); + static lang_memory_region_type *lang_memory_default + PARAMS ((asection *)); ++static lang_output_section_statement_type * lang_output_section_find_1 ++ PARAMS ((const char *, int)); ++static lang_output_section_statement_type * ++ lang_output_section_statement_lookup_1 PARAMS ((const char *, int)); + static void lang_map_flags + PARAMS ((flagword)); + static void init_os +@@ -94,6 +98,9 @@ static lang_statement_union_type *wild_s + static void output_section_callback + PARAMS ((lang_wild_statement_type *, struct wildcard_list *, asection *, + lang_input_statement_type *, PTR)); ++static void check_section_callback ++ PARAMS ((lang_wild_statement_type *, struct wildcard_list *, asection *, ++ lang_input_statement_type *, PTR)); + static lang_input_statement_type *lookup_name + PARAMS ((const char *)); + static bfd_boolean load_symbols +@@ -111,6 +118,9 @@ static void lang_reasonable_defaults + PARAMS ((void)); + static void insert_undefined + PARAMS ((const char *)); ++static void check_input_sections ++ PARAMS ((lang_statement_union_type *, ++ lang_output_section_statement_type *)); + static void lang_place_undefineds + PARAMS ((void)); + static void map_input_to_output_sections +@@ -745,9 +755,10 @@ lang_memory_default (section) + return lang_memory_region_lookup ("*default*"); + } + +-lang_output_section_statement_type * +-lang_output_section_find (name) ++static lang_output_section_statement_type * ++lang_output_section_find_1 (name, constraint) + const char *const name; ++ int constraint; + { + lang_statement_union_type *u; + lang_output_section_statement_type *lookup; +@@ -757,7 +768,9 @@ lang_output_section_find (name) + u = lookup->next) + { + lookup = &u->output_section_statement; +- if (strcmp (name, lookup->name) == 0) ++ if (strcmp (name, lookup->name) == 0 ++ && lookup->constraint != -1 ++ && (constraint == 0 || constraint == lookup->constraint)) + { + return lookup; + } +@@ -766,12 +779,20 @@ lang_output_section_find (name) + } + + lang_output_section_statement_type * +-lang_output_section_statement_lookup (name) ++lang_output_section_find (name) ++ const char *const name; ++{ ++ return lang_output_section_find_1 (name, 0); ++} ++ ++static lang_output_section_statement_type * ++lang_output_section_statement_lookup_1 (name, constraint) + const char *const name; ++ int constraint; + { + lang_output_section_statement_type *lookup; + +- lookup = lang_output_section_find (name); ++ lookup = lang_output_section_find_1 (name, constraint); + if (lookup == (lang_output_section_statement_type *) NULL) + { + +@@ -786,6 +807,7 @@ lang_output_section_statement_lookup (na + lookup->next = (lang_statement_union_type *) NULL; + lookup->bfd_section = (asection *) NULL; + lookup->processed = FALSE; ++ lookup->constraint = constraint; + lookup->sectype = normal_section; + lookup->addr_tree = (etree_type *) NULL; + lang_list_init (&lookup->children); +@@ -805,6 +827,13 @@ lang_output_section_statement_lookup (na + return lookup; + } + ++lang_output_section_statement_type * ++lang_output_section_statement_lookup (name) ++ const char *const name; ++{ ++ return lang_output_section_statement_lookup_1 (name, 0); ++} ++ + static void + lang_map_flags (flag) + flagword flag; +@@ -1482,6 +1511,31 @@ output_section_callback (ptr, sec, secti + } + } + ++/* Check if all sections in a wild statement for a particular FILE ++ are readonly. */ ++ ++static void ++check_section_callback (ptr, sec, section, file, output) ++ lang_wild_statement_type *ptr ATTRIBUTE_UNUSED; ++ struct wildcard_list *sec ATTRIBUTE_UNUSED; ++ asection *section; ++ lang_input_statement_type *file ATTRIBUTE_UNUSED; ++ PTR output; ++{ ++ /* Exclude sections that match UNIQUE_SECTION_LIST. */ ++ if (unique_section_p (bfd_get_section_name (file->the_bfd, section))) ++ return; ++ ++ if (section->output_section == NULL) ++ { ++ flagword flags = bfd_get_section_flags (section->owner, section); ++ ++ if ((flags & SEC_READONLY) == 0) ++ ((lang_output_section_statement_type *) output)->all_input_readonly ++ = FALSE; ++ } ++} ++ + /* This is passed a file name which must have been seen already and + added to the statement tree. We will see if it has been opened + already and had its symbols read. If not then we'll read it. */ +@@ -2151,6 +2205,41 @@ lang_place_undefineds () + } + } + ++/* Check for all readonly or some readwrite sections. */ ++ ++static void ++check_input_sections (s, output_section_statement) ++ lang_statement_union_type *s; ++ lang_output_section_statement_type *output_section_statement; ++{ ++ for (; s != (lang_statement_union_type *) NULL; s = s->header.next) ++ { ++ switch (s->header.type) ++ { ++ case lang_wild_statement_enum: ++ walk_wild (&s->wild_statement, check_section_callback, ++ output_section_statement); ++ if (! output_section_statement->all_input_readonly) ++ return; ++ break; ++ case lang_constructors_statement_enum: ++ check_input_sections (constructor_list.head, ++ output_section_statement); ++ if (! output_section_statement->all_input_readonly) ++ return; ++ break; ++ case lang_group_statement_enum: ++ check_input_sections (s->group_statement.children.head, ++ output_section_statement); ++ if (! output_section_statement->all_input_readonly) ++ return; ++ break; ++ default: ++ break; ++ } ++ } ++} ++ + /* Open input files and attach to output sections. */ + + static void +@@ -2172,6 +2261,23 @@ map_input_to_output_sections (s, target, + output_section_statement); + break; + case lang_output_section_statement_enum: ++ if (s->output_section_statement.constraint) ++ { ++ if (s->output_section_statement.constraint == -1) ++ break; ++ s->output_section_statement.all_input_readonly = TRUE; ++ check_input_sections (s->output_section_statement.children.head, ++ &s->output_section_statement); ++ if ((s->output_section_statement.all_input_readonly ++ && s->output_section_statement.constraint == ONLY_IF_RW) ++ || (!s->output_section_statement.all_input_readonly ++ && s->output_section_statement.constraint == ONLY_IF_RO)) ++ { ++ s->output_section_statement.constraint = -1; ++ break; ++ } ++ } ++ + map_input_to_output_sections (s->output_section_statement.children.head, + target, + &s->output_section_statement); +@@ -2242,6 +2348,8 @@ strip_excluded_output_sections () + asection *s; + + os = &u->output_section_statement; ++ if (os->constraint == -1) ++ continue; + s = os->bfd_section; + if (s != NULL && (s->flags & SEC_EXCLUDE) != 0) + { +@@ -4132,7 +4240,7 @@ topower (x) + lang_output_section_statement_type * + lang_enter_output_section_statement (output_section_statement_name, + address_exp, sectype, block_value, +- align, subalign, ebase) ++ align, subalign, ebase, constraint) + const char *output_section_statement_name; + etree_type *address_exp; + enum section_type sectype; +@@ -4140,12 +4248,14 @@ lang_enter_output_section_statement (out + etree_type *align; + etree_type *subalign; + etree_type *ebase; ++ int constraint; + { + lang_output_section_statement_type *os; + + current_section = + os = +- lang_output_section_statement_lookup (output_section_statement_name); ++ lang_output_section_statement_lookup_1 (output_section_statement_name, ++ constraint); + + /* Add this statement to tree. */ + #if 0 +@@ -4879,6 +4989,8 @@ lang_record_phdrs () + struct lang_output_section_phdr_list *pl; + + os = &u->output_section_statement; ++ if (os->constraint == -1) ++ continue; + + pl = os->phdrs; + if (pl != NULL) +@@ -4939,7 +5051,8 @@ lang_record_phdrs () + { + struct lang_output_section_phdr_list *pl; + +- if (u->output_section_statement.bfd_section == NULL) ++ if (u->output_section_statement.constraint == -1 ++ || u->output_section_statement.bfd_section == NULL) + continue; + + for (pl = u->output_section_statement.phdrs; +@@ -5009,7 +5122,7 @@ lang_enter_overlay_section (name) + etree_type *size; + + lang_enter_output_section_statement (name, overlay_vma, normal_section, +- 0, 0, 0, 0); ++ 0, 0, 0, 0, 0); + + /* If this is the first section, then base the VMA of future + sections on this one. This will work correctly even if `.' is +--- ld/ldlex.l.jj Mon May 5 17:46:49 2003 ++++ ld/ldlex.l Mon May 19 06:31:40 2003 +@@ -303,6 +303,8 @@ V_IDENTIFIER [*?.$_a-zA-Z\[\]\-\!\^]([*? + <EXPRESSION,BOTH,SCRIPT>"COPY" { RTOKEN(COPY);} + <EXPRESSION,BOTH,SCRIPT>"INFO" { RTOKEN(INFO);} + <EXPRESSION,BOTH,SCRIPT>"OVERLAY" { RTOKEN(OVERLAY);} ++<EXPRESSION,BOTH,SCRIPT>"ONLY_IF_RO" { RTOKEN(ONLY_IF_RO); } ++<EXPRESSION,BOTH,SCRIPT>"ONLY_IF_RW" { RTOKEN(ONLY_IF_RW); } + <BOTH,SCRIPT>"o" { RTOKEN(ORIGIN);} + <BOTH,SCRIPT>"org" { RTOKEN(ORIGIN);} + <BOTH,SCRIPT>"l" { RTOKEN( LENGTH);} diff --git a/sys-devel/binutils/files/2.14/binutils-2.14.90.0.4-gas-execstack.patch b/sys-devel/binutils/files/2.14/binutils-2.14.90.0.4-gas-execstack.patch new file mode 100644 index 000000000000..9b04bb119d5b --- /dev/null +++ b/sys-devel/binutils/files/2.14/binutils-2.14.90.0.4-gas-execstack.patch @@ -0,0 +1,92 @@ +2003-06-04 Jakub Jelinek <jakub@redhat.com> + + * as.c (show_usage): Document --execstack and --noexecstack. + (parse_args): Add --execstack and --noexecstack. + (main): Create .note.GNU-stack section if --execstack or + --noexecstack was given on comand line, set its SHF_EXECINSTR bit. + * as.h (flag_execstack, flag_noexecstack): New. + +--- gas/as.c.jj 2003-05-30 09:44:26.000000000 -0400 ++++ gas/as.c 2003-06-04 07:43:05.000000000 -0400 +@@ -268,6 +268,12 @@ Options:\n\ + emulate output (default %s)\n"), def_em); + } + #endif ++#if defined BFD_ASSEMBLER && (defined OBJ_ELF || defined OBJ_MAYBE_ELF) ++ fprintf (stream, _("\ ++ --execstack require executable stack for this object\n")); ++ fprintf (stream, _("\ ++ --noexecstack don't require executable stack for this object\n")); ++#endif + fprintf (stream, _("\ + -f skip whitespace and comment preprocessing\n")); + fprintf (stream, _("\ +@@ -437,7 +443,13 @@ parse_args (pargc, pargv) + {"warn", no_argument, NULL, OPTION_WARN}, + #define OPTION_TARGET_HELP (OPTION_STD_BASE + 19) + {"target-help", no_argument, NULL, OPTION_TARGET_HELP}, +-#define OPTION_WARN_FATAL (OPTION_STD_BASE + 20) ++#if defined BFD_ASSEMBLER && (defined OBJ_ELF || defined OBJ_MAYBE_ELF) ++#define OPTION_EXECSTACK (OPTION_STD_BASE + 20) ++ {"execstack", no_argument, NULL, OPTION_EXECSTACK}, ++#define OPTION_NOEXECSTACK (OPTION_STD_BASE + 21) ++ {"noexecstack", no_argument, NULL, OPTION_NOEXECSTACK}, ++#endif ++#define OPTION_WARN_FATAL (OPTION_STD_BASE + 22) + {"fatal-warnings", no_argument, NULL, OPTION_WARN_FATAL} + /* When you add options here, check that they do not collide with + OPTION_MD_BASE. See as.h. */ +@@ -698,6 +710,18 @@ the GNU General Public License. This pr + flag_fatal_warnings = 1; + break; + ++#if defined BFD_ASSEMBLER && (defined OBJ_ELF || defined OBJ_MAYBE_ELF) ++ case OPTION_EXECSTACK: ++ flag_execstack = 1; ++ flag_noexecstack = 0; ++ break; ++ ++ case OPTION_NOEXECSTACK: ++ flag_noexecstack = 1; ++ flag_execstack = 0; ++ break; ++#endif ++ + case 'Z': + flag_always_generate_output = 1; + break; +@@ -907,6 +931,19 @@ main (argc, argv) + md_end (); + #endif + ++#if defined BFD_ASSEMBLER && (defined OBJ_ELF || defined OBJ_MAYBE_ELF) ++ if ((flag_execstack || flag_noexecstack) ++ && OUTPUT_FLAVOR == bfd_target_elf_flavour) ++ { ++ segT gnustack; ++ ++ gnustack = subseg_new (".note.GNU-stack", 0); ++ bfd_set_section_flags (stdoutput, gnustack, ++ SEC_READONLY | (flag_execstack ? SEC_CODE : 0)); ++ ++ } ++#endif ++ + /* If we've been collecting dwarf2 .debug_line info, either for + assembly debugging or on behalf of the compiler, emit it now. */ + dwarf2_finish (); +--- gas/as.h.jj 2003-05-23 09:24:40.000000000 -0400 ++++ gas/as.h 2003-06-04 05:17:39.000000000 -0400 +@@ -436,6 +436,12 @@ COMMON int flag_strip_local_absolute; + /* True if we should generate a traditional format object file. */ + COMMON int flag_traditional_format; + ++/* TRUE if .note.GNU-stack section with SEC_CODE should be created */ ++COMMON int flag_execstack; ++ ++/* TRUE if .note.GNU-stack section with SEC_CODE should be created */ ++COMMON int flag_noexecstack; ++ + /* name of emitted object file */ + COMMON char *out_file_name; + diff --git a/sys-devel/binutils/files/2.14/binutils-2.14.90.0.4-gas-pred.patch b/sys-devel/binutils/files/2.14/binutils-2.14.90.0.4-gas-pred.patch new file mode 100644 index 000000000000..52097d66210a --- /dev/null +++ b/sys-devel/binutils/files/2.14/binutils-2.14.90.0.4-gas-pred.patch @@ -0,0 +1,46 @@ +2003-06-06 H.J. Lu <hongjiu.lu@intel.com> + + * app.c (do_scrub_chars): Add states 14 and 15 to handle + predicate for ia64. + +--- gas/app.c.pred 2003-04-24 14:19:07.000000000 -0700 ++++ gas/app.c 2003-06-07 07:48:33.000000000 -0700 +@@ -374,6 +374,12 @@ do_scrub_chars (get, tostart, tolen) + 13: After seeing a vertical bar, looking for a second + vertical bar as a parallel expression separator. + #endif ++#ifdef TC_IA64 ++ 14: After seeing a `(' at state 0, looking for a `)' as ++ predicate. ++ 15: After seeing a `(' at state 1, looking for a `)' as ++ predicate. ++#endif + */ + + /* I added states 9 and 10 because the MIPS ECOFF assembler uses +@@ -674,6 +680,25 @@ do_scrub_chars (get, tostart, tolen) + /* flushchar: */ + ch = GET (); + ++#ifdef TC_IA64 ++ if (ch == '(' && (state == 0 || state == 1)) ++ { ++ state += 14; ++ PUT (ch); ++ continue; ++ } ++ else if (state == 14 || state == 15) ++ { ++ if (ch == ')') ++ state -= 14; ++ else ++ { ++ PUT (ch); ++ continue; ++ } ++ } ++#endif ++ + recycle: + + #if defined TC_ARM && defined OBJ_ELF diff --git a/sys-devel/binutils/files/2.14/binutils-2.14.90.0.4-ltconfig-multilib.patch b/sys-devel/binutils/files/2.14/binutils-2.14.90.0.4-ltconfig-multilib.patch new file mode 100644 index 000000000000..26dfb8492c3c --- /dev/null +++ b/sys-devel/binutils/files/2.14/binutils-2.14.90.0.4-ltconfig-multilib.patch @@ -0,0 +1,26 @@ +--- ltconfig.jj 2003-02-03 16:56:49.000000000 +0900 ++++ ltconfig 2003-02-03 16:56:49.000000000 +0900 +@@ -1237,6 +1237,23 @@ + # people can always --disable-shared, the test was removed, and we + # assume the GNU/Linux dynamic linker is in use. + dynamic_linker='GNU/Linux ld.so' ++ ++ # Find out which ABI we are using (multilib hack). ++ case "$host_cpu" in ++ x86_64*|s390*|sparc*|ppc*|powerpc*) ++ echo "$progname:@lineno@: checking multilib ABI type" 1>&5 ++ touch conftest.$ac_ext ++ if { (eval echo $progname: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>conftest.err; } && test -s conftest.$objext; then ++ case `/usr/bin/file conftest.o` in ++ *64-bit*) ++ sys_lib_dlsearch_path_spec="/lib64 /usr/lib64" ++ sys_lib_search_path_spec="/lib64 /usr/lib64 /usr/local/lib64" ++ ;; ++ esac ++ fi ++ rm -rf conftest* ++ ;; ++ esac + ;; + + netbsd*) diff --git a/sys-devel/binutils/files/2.14/binutils-2.14.90.0.4-pie.patch b/sys-devel/binutils/files/2.14/binutils-2.14.90.0.4-pie.patch new file mode 100644 index 000000000000..5d1cf56a4bc6 --- /dev/null +++ b/sys-devel/binutils/files/2.14/binutils-2.14.90.0.4-pie.patch @@ -0,0 +1,632 @@ +2003-05-29 Ulrich Drepper <drepper@redhat.com> + Jakub Jelinek <jakub@redhat.com> + +bfd/ + * elflink.h (elf_link_add_object_symbols): Use !info->executable + instead of info->shared where appropriate. + (bfd_elfNN_size_dynamic_sections, elf_link_output_extsym): Likewise. + * elflink.c (_bfd_elf_create_got_section): Likewise. + (_bfd_elf_link_create_dynamic_sections): Likewise. + (_bfd_elf_link_assign_sym_version): Likewise. + * elf32-i386.c (elf_i386_size_dynamic_sections): Create .interp section + and DT_DEBUG dynamic tag even for position independent executables. + * elf32-ppc.c (ppc_elf_size_dynamic_sections): Likewise. + * elf32-s390.c (elf_s390_size_dynamic_sections: Likewise. + * elf64-ppc.c (ppc64_elf_size_dynamic_sections: Likewise. + * elf64-s390.c (elf_s390_size_dynamic_sections: Likewise. + * elf64-x86-64.c (elf64_x86_64_size_dynamic_sections: Likewise. + * elfxx-ia64.c (elfNN_ia64_size_dynamic_sections: Likewise. + * elf32-sparc.c (elf32_sparc_size_dynamic_sections: Likewise. + * elf64-alpha.c (elf64_alpha_size_dynamic_sections: Likewise. + * elf64-sparc.c (sparc64_elf_size_dynamic_sections: Likewise. +include/ + * bfdlink.h (struct bfd_link_info): Add pie and executable + bits. +ld/ + * lexsup.c (OPTION_PIE): Define. + (ld_options): Add -pie and --pic-executable options. + (parse_args): Handle OPTION_PIE. + * ldmain.c (main): Initialize link_info.pie and + link_info.executable. + * genscripts.sh: Generate PIE scripts. + * ld.texinfo: Document -pie and --pic-executable options. + * emultempl/elf32.em (gld${EMULATION_NAME}_after_open): + (gld${EMULATION_NAME}_place_orphan): Likewise. + (gld${EMULATION_NAME}_get_script): Include PIE scripts. + * scripttempl/elf.sc: In PIE scripts set . the same way as in + shared scripts. + * emulparams/elf_i386.sh (GENERATE_PIE_SCRIPT): Set to yes. + * emulparams/elf64_ia64.sh (GENERATE_PIE_SCRIPT): Likewise. + * emulparams/elf32ppc.sh (GENERATE_PIE_SCRIPT): Likewise. + * emulparams/elf64ppc.sh (GENERATE_PIE_SCRIPT): Likewise. + * emulparams/elf_x86_64.sh (GENERATE_PIE_SCRIPT): Likewise. + * emulparams/elf_s390.sh (GENERATE_PIE_SCRIPT): Likewise. + * emulparams/elf32_sparc.sh (GENERATE_PIE_SCRIPT): Likewise. + * emulparams/elf64_sparc.sh (GENERATE_PIE_SCRIPT): Likewise. + * emulparams/elf64alpha.sh (GENERATE_PIE_SCRIPT): Likewise. + * emulparams/elf64_s390.sh (GENERATE_PIE_SCRIPT): Likewise. + * emulparams/elf_i386.sh (GENERATE_PIE_SCRIPT): Likewise. + +--- bfd/elf32-i386.c.jj 2003-05-23 10:18:52.000000000 -0400 ++++ bfd/elf32-i386.c 2003-05-28 03:18:13.000000000 -0400 +@@ -1797,7 +1797,7 @@ elf_i386_size_dynamic_sections (output_b + if (htab->elf.dynamic_sections_created) + { + /* Set the contents of the .interp section to the interpreter. */ +- if (! info->shared) ++ if (info->executable) + { + s = bfd_get_section_by_name (dynobj, ".interp"); + if (s == NULL) +@@ -1963,7 +1963,7 @@ elf_i386_size_dynamic_sections (output_b + #define add_dynamic_entry(TAG, VAL) \ + bfd_elf32_add_dynamic_entry (info, (bfd_vma) (TAG), (bfd_vma) (VAL)) + +- if (! info->shared) ++ if (info->executable) + { + if (!add_dynamic_entry (DT_DEBUG, 0)) + return FALSE; +--- bfd/elflink.h.jj 2003-05-23 10:18:52.000000000 -0400 ++++ bfd/elflink.h 2003-05-28 06:27:38.000000000 -0400 +@@ -474,7 +474,7 @@ elf_link_add_object_symbols (abfd, info) + .gnu.warning.SYMBOL are treated as warning symbols for the given + symbol. This differs from .gnu.warning sections, which generate + warnings when they are included in an output file. */ +- if (! info->shared) ++ if (info->executable) + { + asection *s; + +@@ -1321,7 +1321,7 @@ elf_link_add_object_symbols (abfd, info) + } + else + new_flag = ELF_LINK_HASH_DEF_REGULAR; +- if (info->shared ++ if (! info->executable + || (old_flags & (ELF_LINK_HASH_DEF_DYNAMIC + | ELF_LINK_HASH_REF_DYNAMIC)) != 0) + dynsym = TRUE; +@@ -2174,7 +2174,7 @@ NAME(bfd_elf,size_dynamic_sections) (out + if (bfd_get_section_by_name (output_bfd, ".preinit_array") != NULL) + { + /* DT_PREINIT_ARRAY is not allowed in shared library. */ +- if (info->shared) ++ if (! info->executable) + { + bfd *sub; + asection *o; +@@ -2440,7 +2440,7 @@ NAME(bfd_elf,size_dynamic_sections) (out + + if (info->flags_1) + { +- if (! info->shared) ++ if (info->executable) + info->flags_1 &= ~ (DF_1_INITFIRST + | DF_1_NODELETE + | DF_1_NOOPEN); +@@ -4417,7 +4417,8 @@ elf_link_output_extsym (h, data) + referenced by regular files, because we will already have issued + warnings for them. */ + if (! finfo->info->relocateable +- && (! finfo->info->shared || ! finfo->info->allow_shlib_undefined) ++ && (finfo->info->executable ++ || ! finfo->info->allow_shlib_undefined) + && h->root.type == bfd_link_hash_undefined + && (h->elf_link_hash_flags & ELF_LINK_HASH_REF_DYNAMIC) != 0 + && (h->elf_link_hash_flags & ELF_LINK_HASH_REF_REGULAR) == 0 +--- bfd/elf32-ppc.c.jj 2003-05-23 10:18:52.000000000 -0400 ++++ bfd/elf32-ppc.c 2003-05-28 03:19:08.000000000 -0400 +@@ -2920,7 +2920,7 @@ ppc_elf_size_dynamic_sections (output_bf + if (elf_hash_table (info)->dynamic_sections_created) + { + /* Set the contents of the .interp section to the interpreter. */ +- if (! info->shared) ++ if (info->executable) + { + s = bfd_get_section_by_name (htab->elf.dynobj, ".interp"); + BFD_ASSERT (s != NULL); +@@ -3102,7 +3102,7 @@ ppc_elf_size_dynamic_sections (output_bf + #define add_dynamic_entry(TAG, VAL) \ + bfd_elf32_add_dynamic_entry (info, (bfd_vma) (TAG), (bfd_vma) (VAL)) + +- if (!info->shared) ++ if (info->executable) + { + if (!add_dynamic_entry (DT_DEBUG, 0)) + return FALSE; +--- bfd/elf32-s390.c.jj 2003-05-15 16:42:24.000000000 -0400 ++++ bfd/elf32-s390.c 2003-05-28 03:19:32.000000000 -0400 +@@ -1927,7 +1927,7 @@ elf_s390_size_dynamic_sections (output_b + if (htab->elf.dynamic_sections_created) + { + /* Set the contents of the .interp section to the interpreter. */ +- if (! info->shared) ++ if (info->executable) + { + s = bfd_get_section_by_name (dynobj, ".interp"); + if (s == NULL) +@@ -2085,7 +2085,7 @@ elf_s390_size_dynamic_sections (output_b + #define add_dynamic_entry(TAG, VAL) \ + bfd_elf32_add_dynamic_entry (info, (bfd_vma) (TAG), (bfd_vma) (VAL)) + +- if (! info->shared) ++ if (info->executable) + { + if (!add_dynamic_entry (DT_DEBUG, 0)) + return FALSE; +--- bfd/elf64-ppc.c.jj 2003-05-23 10:18:52.000000000 -0400 ++++ bfd/elf64-ppc.c 2003-05-28 03:19:51.000000000 -0400 +@@ -5737,7 +5737,7 @@ ppc64_elf_size_dynamic_sections (output_ + if (htab->elf.dynamic_sections_created) + { + /* Set the contents of the .interp section to the interpreter. */ +- if (! info->shared) ++ if (info->executable) + { + s = bfd_get_section_by_name (dynobj, ".interp"); + if (s == NULL) +@@ -5936,7 +5936,7 @@ ppc64_elf_size_dynamic_sections (output_ + #define add_dynamic_entry(TAG, VAL) \ + bfd_elf64_add_dynamic_entry (info, (bfd_vma) (TAG), (bfd_vma) (VAL)) + +- if (!info->shared) ++ if (info->executable) + { + if (!add_dynamic_entry (DT_DEBUG, 0)) + return FALSE; +--- bfd/elf64-s390.c.jj 2003-05-15 16:42:25.000000000 -0400 ++++ bfd/elf64-s390.c 2003-05-28 03:20:08.000000000 -0400 +@@ -1898,7 +1898,7 @@ elf_s390_size_dynamic_sections (output_b + if (htab->elf.dynamic_sections_created) + { + /* Set the contents of the .interp section to the interpreter. */ +- if (! info->shared) ++ if (info->executable) + { + s = bfd_get_section_by_name (dynobj, ".interp"); + if (s == NULL) +@@ -2056,7 +2056,7 @@ elf_s390_size_dynamic_sections (output_b + #define add_dynamic_entry(TAG, VAL) \ + bfd_elf64_add_dynamic_entry (info, (bfd_vma) (TAG), (bfd_vma) (VAL)) + +- if (! info->shared) ++ if (info->executable) + { + if (!add_dynamic_entry (DT_DEBUG, 0)) + return FALSE; +--- bfd/elf64-x86-64.c.jj 2003-05-05 17:46:47.000000000 -0400 ++++ bfd/elf64-x86-64.c 2003-05-28 05:44:30.000000000 -0400 +@@ -1618,7 +1618,7 @@ elf64_x86_64_size_dynamic_sections (outp + if (htab->elf.dynamic_sections_created) + { + /* Set the contents of the .interp section to the interpreter. */ +- if (! info->shared) ++ if (info->executable) + { + s = bfd_get_section_by_name (dynobj, ".interp"); + if (s == NULL) +@@ -1779,7 +1779,7 @@ elf64_x86_64_size_dynamic_sections (outp + #define add_dynamic_entry(TAG, VAL) \ + bfd_elf64_add_dynamic_entry (info, (bfd_vma) (TAG), (bfd_vma) (VAL)) + +- if (! info->shared) ++ if (info->executable) + { + if (!add_dynamic_entry (DT_DEBUG, 0)) + return FALSE; +--- bfd/elfxx-ia64.c.jj 2003-05-15 16:42:25.000000000 -0400 ++++ bfd/elfxx-ia64.c 2003-05-28 03:24:40.000000000 -0400 +@@ -2903,7 +2903,7 @@ elfNN_ia64_size_dynamic_sections (output + + /* Set the contents of the .interp section to the interpreter. */ + if (ia64_info->root.dynamic_sections_created +- && !info->shared) ++ && info->executable) + { + sec = bfd_get_section_by_name (dynobj, ".interp"); + BFD_ASSERT (sec != NULL); +@@ -3078,7 +3078,7 @@ elfNN_ia64_size_dynamic_sections (output + later (in finish_dynamic_sections) but we must add the entries now + so that we get the correct size for the .dynamic section. */ + +- if (!info->shared) ++ if (info->executable) + { + /* The DT_DEBUG entry is filled in by the dynamic linker and used + by the debugger. */ +--- bfd/elf32-sparc.c.jj 2003-05-28 03:03:45.000000000 -0400 ++++ bfd/elf32-sparc.c 2003-05-28 03:20:48.000000000 -0400 +@@ -1820,7 +1820,7 @@ elf32_sparc_size_dynamic_sections (outpu + if (elf_hash_table (info)->dynamic_sections_created) + { + /* Set the contents of the .interp section to the interpreter. */ +- if (! info->shared) ++ if (info->executable) + { + s = bfd_get_section_by_name (dynobj, ".interp"); + BFD_ASSERT (s != NULL); +@@ -1997,7 +1997,7 @@ elf32_sparc_size_dynamic_sections (outpu + #define add_dynamic_entry(TAG, VAL) \ + bfd_elf32_add_dynamic_entry (info, (bfd_vma) (TAG), (bfd_vma) (VAL)) + +- if (!info->shared) ++ if (info->executable) + { + if (!add_dynamic_entry (DT_DEBUG, 0)) + return FALSE; +--- bfd/elf64-alpha.c.jj 2003-05-15 16:42:25.000000000 -0400 ++++ bfd/elf64-alpha.c 2003-05-28 03:21:20.000000000 -0400 +@@ -4090,7 +4090,7 @@ elf64_alpha_size_dynamic_sections (outpu + if (elf_hash_table (info)->dynamic_sections_created) + { + /* Set the contents of the .interp section to the interpreter. */ +- if (!info->shared) ++ if (info->executable) + { + s = bfd_get_section_by_name (dynobj, ".interp"); + BFD_ASSERT (s != NULL); +@@ -4176,7 +4176,7 @@ elf64_alpha_size_dynamic_sections (outpu + #define add_dynamic_entry(TAG, VAL) \ + bfd_elf64_add_dynamic_entry (info, (bfd_vma) (TAG), (bfd_vma) (VAL)) + +- if (!info->shared) ++ if (info->executable) + { + if (!add_dynamic_entry (DT_DEBUG, 0)) + return FALSE; +--- bfd/elf64-sparc.c.jj 2003-05-28 03:03:45.000000000 -0400 ++++ bfd/elf64-sparc.c 2003-05-28 03:21:59.000000000 -0400 +@@ -1781,7 +1781,7 @@ sparc64_elf_size_dynamic_sections (outpu + if (elf_hash_table (info)->dynamic_sections_created) + { + /* Set the contents of the .interp section to the interpreter. */ +- if (! info->shared) ++ if (info->executable) + { + s = bfd_get_section_by_name (dynobj, ".interp"); + BFD_ASSERT (s != NULL); +@@ -1880,7 +1880,7 @@ sparc64_elf_size_dynamic_sections (outpu + struct elf_strtab_hash *dynstr; + struct elf_link_hash_table *eht = elf_hash_table (info); + +- if (!info->shared) ++ if (info->executable) + { + if (!add_dynamic_entry (DT_DEBUG, 0)) + return FALSE; +--- bfd/elflink.c.jj 2003-05-23 10:18:52.000000000 -0400 ++++ bfd/elflink.c 2003-05-28 06:20:40.000000000 -0400 +@@ -94,7 +94,7 @@ _bfd_elf_create_got_section (abfd, info) + h->elf_link_hash_flags |= ELF_LINK_HASH_DEF_REGULAR; + h->type = STT_OBJECT; + +- if (info->shared ++ if (! info->executable + && ! _bfd_elf_link_record_dynamic_symbol (info, h)) + return FALSE; + +@@ -144,7 +144,7 @@ _bfd_elf_link_create_dynamic_sections (a + + /* A dynamically linked executable has a .interp section, but a + shared library does not. */ +- if (! info->shared) ++ if (info->executable) + { + s = bfd_make_section (abfd, ".interp"); + if (s == NULL +@@ -227,7 +227,7 @@ _bfd_elf_link_create_dynamic_sections (a + h->elf_link_hash_flags |= ELF_LINK_HASH_DEF_REGULAR; + h->type = STT_OBJECT; + +- if (info->shared ++ if (! info->executable + && ! _bfd_elf_link_record_dynamic_symbol (info, h)) + return FALSE; + +@@ -295,7 +295,7 @@ _bfd_elf_create_dynamic_sections (abfd, + h->elf_link_hash_flags |= ELF_LINK_HASH_DEF_REGULAR; + h->type = STT_OBJECT; + +- if (info->shared ++ if (! info->executable + && ! _bfd_elf_link_record_dynamic_symbol (info, h)) + return FALSE; + } +@@ -1760,7 +1760,7 @@ _bfd_elf_link_assign_sym_version (h, dat + + /* If we are building an application, we need to create a + version node for this version. */ +- if (t == NULL && ! info->shared) ++ if (t == NULL && info->executable) + { + struct bfd_elf_version_tree **pp; + int version_index; +--- include/bfdlink.h.jj 2003-05-23 10:18:54.000000000 -0400 ++++ include/bfdlink.h 2003-05-28 03:15:38.000000000 -0400 +@@ -291,6 +291,12 @@ struct bfd_link_info + /* TRUE if relaxation is being finalized. */ + unsigned int relax_finalizing: 1; + ++ /* TRUE if generating a position independent executable. */ ++ unsigned int pie: 1; ++ ++ /* TRUE if generating an executable, position independent or not. */ ++ unsigned int executable : 1; ++ + /* Which symbols to strip. */ + enum bfd_link_strip strip; + +--- ld/emulparams/elf_i386.sh.jj 2002-03-07 14:52:39.000000000 -0500 ++++ ld/emulparams/elf_i386.sh 2003-05-28 03:15:38.000000000 -0400 +@@ -9,4 +9,5 @@ MACHINE= + NOP=0x90909090 + TEMPLATE_NAME=elf32 + GENERATE_SHLIB_SCRIPT=yes ++GENERATE_PIE_SCRIPT=yes + NO_SMALL_DATA=yes +--- ld/emulparams/elf64_ia64.sh.jj 2003-05-15 16:42:25.000000000 -0400 ++++ ld/emulparams/elf64_ia64.sh 2003-05-28 03:15:38.000000000 -0400 +@@ -16,6 +16,7 @@ fi + TEXT_START_ADDR="0x4000000000000000" + DATA_ADDR="0x6000000000000000 + (. & (${MAXPAGESIZE} - 1))" + GENERATE_SHLIB_SCRIPT=yes ++GENERATE_PIE_SCRIPT=yes + NOP=0x00300000010070000002000001000400 # a bundle full of nops + OTHER_GOT_SECTIONS=" + .IA_64.pltoff ${RELOCATING-0} : { *(.IA_64.pltoff) }" +--- ld/emulparams/elf32ppc.sh.jj 2003-03-19 12:19:16.000000000 -0500 ++++ ld/emulparams/elf32ppc.sh 2003-05-28 03:15:38.000000000 -0400 +@@ -4,6 +4,7 @@ + TEMPLATE_NAME=elf32 + EXTRA_EM_FILE=ppc32elf + GENERATE_SHLIB_SCRIPT=yes ++GENERATE_PIE_SCRIPT=yes + SCRIPT_NAME=elf + OUTPUT_FORMAT="elf32-powerpc" + TEXT_START_ADDR=0x01800000 +--- ld/emulparams/elf64ppc.sh.jj 2003-01-21 13:21:34.000000000 -0500 ++++ ld/emulparams/elf64ppc.sh 2003-05-28 03:15:38.000000000 -0400 +@@ -2,6 +2,7 @@ TEMPLATE_NAME=elf32 + EXTRA_EM_FILE=ppc64elf + ELFSIZE=64 + GENERATE_SHLIB_SCRIPT=yes ++GENERATE_PIE_SCRIPT=yes + SCRIPT_NAME=elf + OUTPUT_FORMAT="elf64-powerpc" + TEXT_START_ADDR=0x10000000 +--- ld/emulparams/elf_x86_64.sh.jj 2003-03-19 12:19:16.000000000 -0500 ++++ ld/emulparams/elf_x86_64.sh 2003-05-28 03:15:38.000000000 -0400 +@@ -10,6 +10,7 @@ MACHINE= + NOP=0x90909090 + TEMPLATE_NAME=elf32 + GENERATE_SHLIB_SCRIPT=yes ++GENERATE_PIE_SCRIPT=yes + NO_SMALL_DATA=yes + + if [ "x${host}" = "x${target}" ]; then +--- ld/emulparams/elf_s390.sh.jj 2002-03-07 14:52:39.000000000 -0500 ++++ ld/emulparams/elf_s390.sh 2003-05-28 03:15:38.000000000 -0400 +@@ -8,3 +8,4 @@ MACHINE= + NOP=0x07070707 + TEMPLATE_NAME=elf32 + GENERATE_SHLIB_SCRIPT=yes ++GENERATE_PIE_SCRIPT=yes +--- ld/emulparams/elf64_sparc.sh.jj 2003-03-19 12:19:16.000000000 -0500 ++++ ld/emulparams/elf64_sparc.sh 2003-05-28 03:30:35.000000000 -0400 +@@ -8,6 +8,7 @@ ARCH="sparc:v9" + MACHINE= + DATA_PLT= + GENERATE_SHLIB_SCRIPT=yes ++GENERATE_PIE_SCRIPT=yes + NOP=0x01000000 + NO_SMALL_DATA=yes + +--- ld/emulparams/elf32_sparc.sh.jj 2002-03-07 14:52:39.000000000 -0500 ++++ ld/emulparams/elf32_sparc.sh 2003-05-28 03:30:49.000000000 -0400 +@@ -10,4 +10,5 @@ MACHINE= + TEMPLATE_NAME=elf32 + DATA_PLT= + GENERATE_SHLIB_SCRIPT=yes ++GENERATE_PIE_SCRIPT=yes + NO_SMALL_DATA=yes +--- ld/emulparams/elf64alpha.sh.jj 2003-03-19 12:19:16.000000000 -0500 ++++ ld/emulparams/elf64alpha.sh 2003-05-28 03:31:11.000000000 -0400 +@@ -11,6 +11,7 @@ NONPAGED_TEXT_START_ADDR="0x120000000" + ARCH=alpha + MACHINE= + GENERATE_SHLIB_SCRIPT=yes ++GENERATE_PIE_SCRIPT=yes + DATA_PLT= + # Note that the number is always big-endian, thus we have to + # reverse the digit string. +--- ld/emulparams/elf64_s390.sh.jj 2003-03-19 12:19:16.000000000 -0500 ++++ ld/emulparams/elf64_s390.sh 2003-05-28 03:31:25.000000000 -0400 +@@ -9,6 +9,7 @@ MACHINE= + NOP=0x07070707 + TEMPLATE_NAME=elf32 + GENERATE_SHLIB_SCRIPT=yes ++GENERATE_PIE_SCRIPT=yes + + # Treat a host that matches the target with the possible exception of "x" + # in the name as if it were native. +--- ld/emultempl/elf32.em.jj 2003-05-28 03:03:45.000000000 -0400 ++++ ld/emultempl/elf32.em 2003-05-28 05:37:00.000000000 -0400 +@@ -643,7 +643,7 @@ gld${EMULATION_NAME}_after_open () + struct bfd_link_needed_list *needed, *l; + + /* We only need to worry about this when doing a final link. */ +- if (link_info.relocateable || link_info.shared) ++ if (link_info.relocateable || !link_info.executable) + return; + + /* Get the list of files which appear in DT_NEEDED entries in +@@ -1181,7 +1181,7 @@ gld${EMULATION_NAME}_place_orphan (file, + + /* If this is a final link, then always put .gnu.warning.SYMBOL + sections into the .text section to get them out of the way. */ +- if (! link_info.shared ++ if (link_info.executable + && ! link_info.relocateable + && strncmp (secname, ".gnu.warning.", sizeof ".gnu.warning." - 1) == 0 + && hold_text.os != NULL) +@@ -1475,6 +1475,14 @@ if cmp -s ldscripts/${EMULATION_NAME}.x + echo ' ; else if (!config.magic_demand_paged) return' >> e${EMULATION_NAME}.c + sed $sc ldscripts/${EMULATION_NAME}.xn >> e${EMULATION_NAME}.c + fi ++if test -n "$GENERATE_PIE_SCRIPT" ; then ++if test -n "$GENERATE_COMBRELOC_SCRIPT" ; then ++echo ' ; else if (link_info.pie && link_info.combreloc) return' >> e${EMULATION_NAME}.c ++sed $sc ldscripts/${EMULATION_NAME}.xdc >> e${EMULATION_NAME}.c ++fi ++echo ' ; else if (link_info.pie) return' >> e${EMULATION_NAME}.c ++sed $sc ldscripts/${EMULATION_NAME}.xd >> e${EMULATION_NAME}.c ++fi + if test -n "$GENERATE_SHLIB_SCRIPT" ; then + if test -n "$GENERATE_COMBRELOC_SCRIPT" ; then + echo ' ; else if (link_info.shared && link_info.combreloc) return' >> e${EMULATION_NAME}.c +@@ -1512,6 +1520,18 @@ cat >>e${EMULATION_NAME}.c <<EOF + return "ldscripts/${EMULATION_NAME}.xn"; + EOF + fi ++if test -n "$GENERATE_PIE_SCRIPT" ; then ++if test -n "$GENERATE_COMBRELOC_SCRIPT" ; then ++cat >>e${EMULATION_NAME}.c <<EOF ++ else if (link_info.pie && link_info.combreloc) ++ return "ldscripts/${EMULATION_NAME}.xdc"; ++EOF ++fi ++cat >>e${EMULATION_NAME}.c <<EOF ++ else if (link_info.pie) ++ return "ldscripts/${EMULATION_NAME}.xd"; ++EOF ++fi + if test -n "$GENERATE_SHLIB_SCRIPT" ; then + if test -n "$GENERATE_COMBRELOC_SCRIPT" ; then + cat >>e${EMULATION_NAME}.c <<EOF +--- ld/scripttempl/elf.sc.jj 2003-05-28 03:03:45.000000000 -0400 ++++ ld/scripttempl/elf.sc 2003-05-28 03:15:38.000000000 -0400 +@@ -180,8 +180,9 @@ ${RELOCATING- /* For some reason, the So + SECTIONS + { + /* Read-only sections, merged into text segment: */ +- ${CREATE_SHLIB-${RELOCATING+. = ${TEXT_BASE_ADDRESS};}} ++ ${CREATE_SHLIB-${CREATE_PIE-${RELOCATING+. = ${TEXT_BASE_ADDRESS};}}} + ${CREATE_SHLIB+${RELOCATING+. = ${SHLIB_TEXT_START_ADDR:-0} + SIZEOF_HEADERS;}} ++ ${CREATE_PIE+${RELOCATING+. = ${SHLIB_TEXT_START_ADDR:-0} + SIZEOF_HEADERS;}} + ${CREATE_SHLIB-${INTERP}} + ${INITIAL_READONLY_SECTIONS} + ${TEXT_DYNAMIC+${DYNAMIC}} +--- ld/lexsup.c.jj 2003-05-15 16:42:25.000000000 -0400 ++++ ld/lexsup.c 2003-05-28 03:15:38.000000000 -0400 +@@ -139,6 +139,7 @@ int parsing_defsym = 0; + #define OPTION_NO_STRIP_DISCARDED (OPTION_STRIP_DISCARDED + 1) + #define OPTION_ACCEPT_UNKNOWN_INPUT_ARCH (OPTION_NO_STRIP_DISCARDED + 1) + #define OPTION_NO_ACCEPT_UNKNOWN_INPUT_ARCH (OPTION_ACCEPT_UNKNOWN_INPUT_ARCH + 1) ++#define OPTION_PIE (OPTION_NO_ACCEPT_UNKNOWN_INPUT_ARCH + 1) + + /* The long options. This structure is used for both the option + parsing and the help text. */ +@@ -373,6 +374,10 @@ static const struct ld_option ld_options + '\0', NULL, N_("Create a shared library"), ONE_DASH }, + { {"Bshareable", no_argument, NULL, OPTION_SHARED }, /* FreeBSD. */ + '\0', NULL, NULL, ONE_DASH }, ++ { {"pie", no_argument, NULL, OPTION_PIE}, ++ '\0', NULL, N_("Create a position independent executable"), ONE_DASH }, ++ { {"pic-executable", no_argument, NULL, OPTION_PIE}, ++ '\0', NULL, NULL, TWO_DASHES }, + { {"sort-common", no_argument, NULL, OPTION_SORT_COMMON}, + '\0', NULL, N_("Sort common symbols by size"), TWO_DASHES }, + { {"sort_common", no_argument, NULL, OPTION_SORT_COMMON}, +@@ -958,6 +961,15 @@ parse_args (argc, argv) + else + einfo (_("%P%F: -shared not supported\n")); + break; ++ case OPTION_PIE: ++ if (config.has_shared) ++ { ++ link_info.shared = TRUE; ++ link_info.pie = TRUE; ++ } ++ else ++ einfo (_("%P%F: -pie not supported\n")); ++ break; + case 'h': /* Used on Solaris. */ + case OPTION_SONAME: + command_line.soname = optarg; +--- ld/genscripts.sh.jj 2003-03-19 12:19:16.000000000 -0500 ++++ ld/genscripts.sh 2003-05-28 03:15:38.000000000 -0400 +@@ -227,6 +227,31 @@ if test -n "$GENERATE_SHLIB_SCRIPT"; the + rm -f ${COMBRELOC} + COMBRELOC= + fi ++ unset CREATE_SHLIB ++fi ++ ++if test -n "$GENERATE_PIE_SCRIPT"; then ++ LD_FLAG=pie ++ DATA_ALIGNMENT=${DATA_ALIGNMENT_s-${DATA_ALIGNMENT_}} ++ CREATE_PIE=" " ++ # Note that TEXT_START_ADDR is set to NONPAGED_TEXT_START_ADDR. ++ ( ++ echo "/* Script for ld -pie: link position independent executable */" ++ . ${srcdir}/emulparams/${EMULATION_NAME}.sh ++ . ${srcdir}/scripttempl/${SCRIPT_NAME}.sc ++ ) | sed -e '/^ *$/d;s/[ ]*$//' > ldscripts/${EMULATION_NAME}.xd ++ if test -n "$GENERATE_COMBRELOC_SCRIPT"; then ++ LD_FLAG=cpie ++ DATA_ALIGNMENT=${DATA_ALIGNMENT_sc-${DATA_ALIGNMENT}} ++ COMBRELOC=ldscripts/${EMULATION_NAME}.xc.tmp ++ ( echo "/* Script for -pie -z combreloc: position independent executable, combine & sort relocs */" ++ . ${srcdir}/emulparams/${EMULATION_NAME}.sh ++ . ${srcdir}/scripttempl/${SCRIPT_NAME}.sc ++ ) | sed -e '/^ *$/d;s/[ ]*$//' > ldscripts/${EMULATION_NAME}.xdc ++ rm -f ${COMBRELOC} ++ COMBRELOC= ++ fi ++ unset CREATE_PIE + fi + + case " $EMULATION_LIBPATH " in +--- ld/ldmain.c.jj 2003-05-15 16:42:25.000000000 -0400 ++++ ld/ldmain.c 2003-05-28 03:15:38.000000000 -0400 +@@ -291,6 +291,8 @@ main (argc, argv) + link_info.emitrelocations = FALSE; + link_info.task_link = FALSE; + link_info.shared = FALSE; ++ link_info.pie = FALSE; ++ link_info.executable = FALSE; + link_info.symbolic = FALSE; + link_info.export_dynamic = FALSE; + link_info.static_link = FALSE; +@@ -368,6 +370,9 @@ main (argc, argv) + einfo (_("%P%F: -f may not be used without -shared\n")); + } + ++ if (! link_info.shared || link_info.pie) ++ link_info.executable = TRUE; ++ + /* Treat ld -r -s as ld -r -S -x (i.e., strip all local symbols). I + don't see how else this can be handled, since in this case we + must preserve all externally visible symbols. */ +--- ld/ld.texinfo.jj 2003-05-05 17:46:49.000000000 -0400 ++++ ld/ld.texinfo 2003-05-29 07:35:25.000000000 -0400 +@@ -1209,6 +1209,18 @@ command @code{OUTPUT_FORMAT} can also sp + this option overrides it. @xref{BFD}. + @end ifclear + ++@kindex -pie ++@kindex --pic-executable ++@item -pie ++@itemx --pic-executable ++@cindex position independent executables ++Create a position independent executable. This is currently only supported on ++ELF platforms. Position independent executables are similar to shared ++libraries in that they are relocated by the dynamic linker to the virtual ++address OS chooses for them (which can varry between invocations), like ++normal dynamically linked executables they can be executed and symbols ++defined in the executable cannot be overridden by shared libraries. ++ + @kindex -qmagic + @item -qmagic + This option is ignored for Linux compatibility. diff --git a/sys-devel/binutils/files/2.14/binutils-2.14.90.0.4-pie2.patch b/sys-devel/binutils/files/2.14/binutils-2.14.90.0.4-pie2.patch new file mode 100644 index 000000000000..d523059d5514 --- /dev/null +++ b/sys-devel/binutils/files/2.14/binutils-2.14.90.0.4-pie2.patch @@ -0,0 +1,25 @@ +2003-06-06 Jakub Jelinek <jakub@redhat.com> + + * elf-bfd.h (SYMBOL_REFERENCES_LOCAL, SYMBOL_CALLS_LOCAL): Return + true even if -pie. + +--- bfd/elf-bfd.h.jj 2003-06-03 18:25:09.000000000 -0400 ++++ bfd/elf-bfd.h 2003-06-06 11:30:25.000000000 -0400 +@@ -217,7 +217,7 @@ struct elf_link_hash_entry + it's necessary for shared libs to also reference the .plt even + though the symbol is really local to the shared lib. */ + #define SYMBOL_REFERENCES_LOCAL(INFO, H) \ +- ((! (INFO)->shared \ ++ (((INFO)->executable \ + || (INFO)->symbolic \ + || (H)->dynindx == -1 \ + || ELF_ST_VISIBILITY ((H)->other) == STV_INTERNAL \ +@@ -227,7 +227,7 @@ struct elf_link_hash_entry + + /* Will _calls_ to this symbol always call the version in this object? */ + #define SYMBOL_CALLS_LOCAL(INFO, H) \ +- ((! (INFO)->shared \ ++ (((INFO)->executable \ + || (INFO)->symbolic \ + || (H)->dynindx == -1 \ + || ELF_ST_VISIBILITY ((H)->other) != STV_DEFAULT \ diff --git a/sys-devel/binutils/files/2.14/binutils-2.14.90.0.4-pni.patch b/sys-devel/binutils/files/2.14/binutils-2.14.90.0.4-pni.patch new file mode 100644 index 000000000000..13e675161613 --- /dev/null +++ b/sys-devel/binutils/files/2.14/binutils-2.14.90.0.4-pni.patch @@ -0,0 +1,442 @@ +gas/ + +2003-05-05 H.J. Lu <hongjiu.lu@intel.com> + + * gas/config/tc-i386.c (md_assemble): Support Intel Precott New + Instructions. + + * gas/config/tc-i386.h (CpuPNI): New. + (CpuUnknownFlags): Add CpuPNI. + +gas/testsuite/ + +2003-05-05 H.J. Lu <hongjiu.lu@intel.com> + + * gas/i386/i386.exp: Add prescott. + + * gas/i386/prescott.d: New file. + * gas/i386/prescott.s: Likewise. + +include/opcode/ + +2003-05-05 H.J. Lu <hongjiu.lu@intel.com> + + * i386.h (i386_optab): Support Intel Precott New Instructions. + +opcodes/ + +2003-05-05 H.J. Lu <hongjiu.lu@intel.com> + + * i386-dis.c (PNI_Fixup): New. Fix up "mwait" and "monitor" in + Intel Precott New Instructions. + (PREGRP27): New. Added for "addsubpd" and "addsubps". + (PREGRP28): New. Added for "haddpd" and "haddps". + (PREGRP29): New. Added for "hsubpd" and "hsubps". + (PREGRP30): New. Added for "movsldup" and "movddup". + (PREGRP31): New. Added for "movshdup" and "movhpd". + (PREGRP32): New. Added for "lddqu". + (dis386_twobyte): Use PREGRP30 to replace the "movlpX" entry. + Use PREGRP31 to replace the "movhpX" entry. Use PREGRP28 for + entry 0x7c. Use PREGRP29 for entry 0x7d. Use PREGRP27 for + entry 0xd0. Use PREGRP32 for entry 0xf0. + (twobyte_has_modrm): Updated. + (twobyte_uses_SSE_prefix): Likewise. + (grps): Use PNI_Fixup in the "sidtQ" entry. + (prefix_user_table): Add PREGRP27, PREGRP28, PREGRP29, PREGRP30, + PREGRP31 and PREGRP32. + (float_mem): Use "fisttp{l||l|}" in entry 1 in opcode 0xdb. + Use "fisttpll" in entry 1 in opcode 0xdd. + Use "fisttp" in entry 1 in opcode 0xdf. + +--- gas/config/tc-i386.c.pni 2003-02-27 11:27:09.000000000 -0800 ++++ gas/config/tc-i386.c 2003-05-05 08:27:55.000000000 -0700 +@@ -1392,6 +1392,21 @@ md_assemble (line) + + if (i.tm.opcode_modifier & ImmExt) + { ++ if ((i.tm.cpu_flags & CpuPNI) && i.operands > 0) ++ { ++ /* These Intel Precott New Instructions have the fixed ++ operands with an opcode suffix which is coded in the same ++ place as an 8-bit immediate field would be. Here we check ++ those operands and remove them afterwards. */ ++ unsigned int x; ++ ++ for (x = 0; x < i.operands; x++) ++ if (i.op[x].regs->reg_num != x) ++ as_bad (_("can't use register '%%%s' as operand %d in '%s'."), ++ i.op[x].regs->reg_name, x + 1, i.tm.name); ++ i.operands = 0; ++ } ++ + /* These AMD 3DNow! and Intel Katmai New Instructions have an + opcode suffix which is coded in the same place as an 8-bit + immediate field would be. Here we fake an 8-bit immediate +--- gas/config/tc-i386.h.pni 2003-01-23 09:20:47.000000000 -0800 ++++ gas/config/tc-i386.h 2003-05-05 08:27:55.000000000 -0700 +@@ -243,13 +243,14 @@ typedef struct + #define CpuSSE 0x1000 /* Streaming SIMD extensions required */ + #define CpuSSE2 0x2000 /* Streaming SIMD extensions 2 required */ + #define Cpu3dnow 0x4000 /* 3dnow! support required */ ++#define CpuPNI 0x8000 /* Prescott New Instuctions required */ + + /* These flags are set by gas depending on the flag_code. */ + #define Cpu64 0x4000000 /* 64bit support required */ + #define CpuNo64 0x8000000 /* Not supported in the 64bit mode */ + + /* The default value for unknown CPUs - enable all features to avoid problems. */ +-#define CpuUnknownFlags (Cpu086|Cpu186|Cpu286|Cpu386|Cpu486|Cpu586|Cpu686|CpuP4|CpuSledgehammer|CpuMMX|CpuSSE|CpuSSE2|Cpu3dnow|CpuK6|CpuAthlon) ++#define CpuUnknownFlags (Cpu086|Cpu186|Cpu286|Cpu386|Cpu486|Cpu586|Cpu686|CpuP4|CpuSledgehammer|CpuMMX|CpuSSE|CpuSSE2|CpuPNI|Cpu3dnow|CpuK6|CpuAthlon) + + /* the bits in opcode_modifier are used to generate the final opcode from + the base_opcode. These bits also are used to detect alternate forms of +--- gas/testsuite/gas/i386/i386.exp.pni 2002-11-06 09:20:11.000000000 -0800 ++++ gas/testsuite/gas/i386/i386.exp 2003-05-05 08:54:06.000000000 -0700 +@@ -56,6 +56,7 @@ if [expr ([istarget "i*86-*-*"] || [ist + run_dump_test "absrel" + run_dump_test "pcrel" + run_dump_test "sub" ++ run_dump_test "prescott" + + # PIC is only supported on ELF targets. + if { ([istarget "*-*-elf*"] || [istarget "*-*-linux*"] ) +--- gas/testsuite/gas/i386/prescott.d.pni 2003-05-05 08:53:28.000000000 -0700 ++++ gas/testsuite/gas/i386/prescott.d 2003-05-05 09:23:20.000000000 -0700 +@@ -0,0 +1,37 @@ ++#objdump: -dw ++#name: i386 prescott ++ ++.*: +file format .* ++ ++Disassembly of section .text: ++ ++0+000 <foo>: ++ 0: 66 0f d0 01 [ ]*addsubpd \(%ecx\),%xmm0 ++ 4: 66 0f d0 ca [ ]*addsubpd %xmm2,%xmm1 ++ 8: f2 0f d0 13 [ ]*addsubps \(%ebx\),%xmm2 ++ c: f2 0f d0 dc [ ]*addsubps %xmm4,%xmm3 ++ 10: df 88 90 90 90 90 [ ]*fisttp 0x90909090\(%eax\) ++ 16: db 88 90 90 90 90 [ ]*fisttpl 0x90909090\(%eax\) ++ 1c: dd 88 90 90 90 90 [ ]*fisttpll 0x90909090\(%eax\) ++ 22: dd 88 90 90 90 90 [ ]*fisttpll 0x90909090\(%eax\) ++ 28: dd 88 90 90 90 90 [ ]*fisttpll 0x90909090\(%eax\) ++ 2e: 66 0f 7c 65 00 [ ]*haddpd 0x0\(%ebp\),%xmm4 ++ 33: 66 0f 7c ee [ ]*haddpd %xmm6,%xmm5 ++ 37: f2 0f 7c 37 [ ]*haddps \(%edi\),%xmm6 ++ 3b: f2 0f 7c f8 [ ]*haddps %xmm0,%xmm7 ++ 3f: 66 0f 7d c1 [ ]*hsubpd %xmm1,%xmm0 ++ 43: 66 0f 7d 0a [ ]*hsubpd \(%edx\),%xmm1 ++ 47: f2 0f 7d d2 [ ]*hsubps %xmm2,%xmm2 ++ 4b: f2 0f 7d 1c 24 [ ]*hsubps \(%esp,1\),%xmm3 ++ 50: f2 0f f0 2e [ ]*lddqu \(%esi\),%xmm5 ++ 54: 0f 01 c8 [ ]*monitor %eax,%ecx,%edx ++ 57: 0f 01 c8 [ ]*monitor %eax,%ecx,%edx ++ 5a: f2 0f 12 f7 [ ]*movddup %xmm7,%xmm6 ++ 5e: f2 0f 12 38 [ ]*movddup \(%eax\),%xmm7 ++ 62: f3 0f 16 01 [ ]*movshdup \(%ecx\),%xmm0 ++ 66: f3 0f 16 ca [ ]*movshdup %xmm2,%xmm1 ++ 6a: f3 0f 12 13 [ ]*movsldup \(%ebx\),%xmm2 ++ 6e: f3 0f 12 dc [ ]*movsldup %xmm4,%xmm3 ++ 72: 0f 01 c9 [ ]*mwait %eax,%ecx ++ 75: 0f 01 c9 [ ]*mwait %eax,%ecx ++ ... +--- gas/testsuite/gas/i386/prescott.s.pni 2003-05-05 08:53:31.000000000 -0700 ++++ gas/testsuite/gas/i386/prescott.s 2003-05-05 08:46:29.000000000 -0700 +@@ -0,0 +1,34 @@ ++#Prescott New Instructions ++ ++ .text ++foo: ++ addsubpd (%ecx),%xmm0 ++ addsubpd %xmm2,%xmm1 ++ addsubps (%ebx),%xmm2 ++ addsubps %xmm4,%xmm3 ++ fisttp 0x90909090(%eax) ++ fisttpl 0x90909090(%eax) ++ fisttpd 0x90909090(%eax) ++ fisttpq 0x90909090(%eax) ++ fisttpll 0x90909090(%eax) ++ haddpd 0x0(%ebp),%xmm4 ++ haddpd %xmm6,%xmm5 ++ haddps (%edi),%xmm6 ++ haddps %xmm0,%xmm7 ++ hsubpd %xmm1,%xmm0 ++ hsubpd (%edx),%xmm1 ++ hsubps %xmm2,%xmm2 ++ hsubps (%esp,1),%xmm3 ++ lddqu (%esi),%xmm5 ++ monitor ++ monitor %eax,%ecx,%edx ++ movddup %xmm7,%xmm6 ++ movddup (%eax),%xmm7 ++ movshdup (%ecx),%xmm0 ++ movshdup %xmm2,%xmm1 ++ movsldup (%ebx),%xmm2 ++ movsldup %xmm4,%xmm3 ++ mwait ++ mwait %eax,%ecx ++ ++ .p2align 4,0 +--- include/opcode/i386.h.pni 2002-07-08 08:39:20.000000000 -0700 ++++ include/opcode/i386.h 2003-05-05 08:27:55.000000000 -0700 +@@ -1302,6 +1302,30 @@ static const template i386_optab[] = { + {"punpckhqdq",2, 0x660f6d, X, CpuSSE2, FP|Modrm, { RegXMM|LLongMem, RegXMM, 0 } }, + {"punpcklqdq",2, 0x660f6c, X, CpuSSE2, FP|Modrm, { RegXMM|LLongMem, RegXMM, 0 } }, + ++/* Prescott New Instructions. */ ++ ++{"addsubpd", 2, 0x660fd0, X, CpuPNI, FP|Modrm, { RegXMM|LLongMem, RegXMM, 0 } }, ++{"addsubps", 2, 0xf20fd0, X, CpuPNI, FP|Modrm, { RegXMM|LLongMem, RegXMM, 0 } }, ++{"fisttp", 1, 0xdf, 1, CpuPNI, sl_FP|FloatMF|Modrm, { ShortMem|LongMem, 0, 0} }, ++/* Intel Syntax */ ++{"fisttpd", 1, 0xdd, 1, CpuPNI, FP|Modrm, { LLongMem, 0, 0} }, ++{"fisttpq", 1, 0xdd, 1, CpuPNI, FP|Modrm, { LLongMem, 0, 0} }, ++{"fisttpll", 1, 0xdd, 1, CpuPNI, FP|Modrm, { LLongMem, 0, 0} }, ++{"haddpd", 2, 0x660f7c, X, CpuPNI, FP|Modrm, { RegXMM|LLongMem, RegXMM, 0 } }, ++{"haddps", 2, 0xf20f7c, X, CpuPNI, FP|Modrm, { RegXMM|LLongMem, RegXMM, 0 } }, ++{"hsubpd", 2, 0x660f7d, X, CpuPNI, FP|Modrm, { RegXMM|LLongMem, RegXMM, 0 } }, ++{"hsubps", 2, 0xf20f7d, X, CpuPNI, FP|Modrm, { RegXMM|LLongMem, RegXMM, 0 } }, ++{"lddqu", 2, 0xf20ff0, X, CpuPNI, FP|Modrm, { LLongMem, RegXMM, 0 } }, ++{"monitor", 0, 0x0f01, 0xc8, CpuPNI, FP|ImmExt, { 0, 0, 0} }, ++/* Need to ensure only "monitor %eax,%ecx,%edx" is accepted. */ ++{"monitor", 3, 0x0f01, 0xc8, CpuPNI, FP|ImmExt, { Reg32, Reg32, Reg32} }, ++{"movddup", 2, 0xf20f12, X, CpuPNI, FP|Modrm, { RegXMM|LLongMem, RegXMM, 0 } }, ++{"movshdup", 2, 0xf30f16, X, CpuPNI, FP|Modrm, { RegXMM|LLongMem, RegXMM, 0 } }, ++{"movsldup", 2, 0xf30f12, X, CpuPNI, FP|Modrm, { RegXMM|LLongMem, RegXMM, 0 } }, ++{"mwait", 0, 0x0f01, 0xc9, CpuPNI, FP|ImmExt, { 0, 0, 0} }, ++/* Need to ensure only "mwait %eax,%ecx" is accepted. */ ++{"mwait", 2, 0x0f01, 0xc9, CpuPNI, FP|ImmExt, { Reg32, Reg32, 0} }, ++ + /* AMD 3DNow! instructions. */ + + {"prefetch", 1, 0x0f0d, 0, Cpu3dnow, FP|Modrm, { ByteMem, 0, 0 } }, +--- opcodes/i386-dis.c.pni 2003-03-24 09:53:02.000000000 -0800 ++++ opcodes/i386-dis.c 2003-05-05 08:27:55.000000000 -0700 +@@ -93,6 +93,7 @@ static void OP_XS PARAMS ((int, int)); + static void OP_3DNowSuffix PARAMS ((int, int)); + static void OP_SIMD_Suffix PARAMS ((int, int)); + static void SIMD_Fixup PARAMS ((int, int)); ++static void PNI_Fixup PARAMS ((int, int)); + static void BadOp PARAMS ((void)); + + struct dis_private { +@@ -417,6 +418,12 @@ fetch_data (info, addr) + #define PREGRP24 NULL, NULL, USE_PREFIX_USER_TABLE, NULL, 24, NULL, 0 + #define PREGRP25 NULL, NULL, USE_PREFIX_USER_TABLE, NULL, 25, NULL, 0 + #define PREGRP26 NULL, NULL, USE_PREFIX_USER_TABLE, NULL, 26, NULL, 0 ++#define PREGRP27 NULL, NULL, USE_PREFIX_USER_TABLE, NULL, 27, NULL, 0 ++#define PREGRP28 NULL, NULL, USE_PREFIX_USER_TABLE, NULL, 28, NULL, 0 ++#define PREGRP29 NULL, NULL, USE_PREFIX_USER_TABLE, NULL, 29, NULL, 0 ++#define PREGRP30 NULL, NULL, USE_PREFIX_USER_TABLE, NULL, 30, NULL, 0 ++#define PREGRP31 NULL, NULL, USE_PREFIX_USER_TABLE, NULL, 31, NULL, 0 ++#define PREGRP32 NULL, NULL, USE_PREFIX_USER_TABLE, NULL, 32, NULL, 0 + + #define X86_64_0 NULL, NULL, X86_64_SPECIAL, NULL, 0, NULL, 0 + +@@ -776,11 +783,11 @@ static const struct dis386 dis386_twobyt + /* 10 */ + { PREGRP8 }, + { PREGRP9 }, +- { "movlpX", XM, EX, SIMD_Fixup, 'h' }, /* really only 2 operands */ ++ { PREGRP30 }, + { "movlpX", EX, XM, SIMD_Fixup, 'h' }, + { "unpcklpX", XM, EX, XX }, + { "unpckhpX", XM, EX, XX }, +- { "movhpX", XM, EX, SIMD_Fixup, 'l' }, ++ { PREGRP31 }, + { "movhpX", EX, XM, SIMD_Fixup, 'l' }, + /* 18 */ + { GRP14 }, +@@ -895,8 +902,8 @@ static const struct dis386 dis386_twobyt + { "(bad)", XX, XX, XX }, + { "(bad)", XX, XX, XX }, + { "(bad)", XX, XX, XX }, +- { "(bad)", XX, XX, XX }, +- { "(bad)", XX, XX, XX }, ++ { PREGRP28 }, ++ { PREGRP29 }, + { PREGRP23 }, + { PREGRP20 }, + /* 80 */ +@@ -990,7 +997,7 @@ static const struct dis386 dis386_twobyt + { "bswap", RMeSI, XX, XX }, + { "bswap", RMeDI, XX, XX }, + /* d0 */ +- { "(bad)", XX, XX, XX }, ++ { PREGRP27 }, + { "psrlw", MX, EM, XX }, + { "psrld", MX, EM, XX }, + { "psrlq", MX, EM, XX }, +@@ -1026,7 +1033,7 @@ static const struct dis386 dis386_twobyt + { "pmaxsw", MX, EM, XX }, + { "pxor", MX, EM, XX }, + /* f0 */ +- { "(bad)", XX, XX, XX }, ++ { PREGRP32 }, + { "psllw", MX, EM, XX }, + { "pslld", MX, EM, XX }, + { "psllq", MX, EM, XX }, +@@ -1078,15 +1085,15 @@ static const unsigned char twobyte_has_m + /* 40 */ 1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1, /* 4f */ + /* 50 */ 1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1, /* 5f */ + /* 60 */ 1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1, /* 6f */ +- /* 70 */ 1,1,1,1,1,1,1,0,0,0,0,0,0,0,1,1, /* 7f */ ++ /* 70 */ 1,1,1,1,1,1,1,0,0,0,0,0,1,1,1,1, /* 7f */ + /* 80 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* 8f */ + /* 90 */ 1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1, /* 9f */ + /* a0 */ 0,0,0,1,1,1,0,0,0,0,0,1,1,1,1,1, /* af */ + /* b0 */ 1,1,1,1,1,1,1,1,0,0,1,1,1,1,1,1, /* bf */ + /* c0 */ 1,1,1,1,1,1,1,1,0,0,0,0,0,0,0,0, /* cf */ +- /* d0 */ 0,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1, /* df */ ++ /* d0 */ 1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1, /* df */ + /* e0 */ 1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1, /* ef */ +- /* f0 */ 0,1,1,1,1,1,1,1,1,1,1,1,1,1,1,0 /* ff */ ++ /* f0 */ 1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,0 /* ff */ + /* ------------------------------- */ + /* 0 1 2 3 4 5 6 7 8 9 a b c d e f */ + }; +@@ -1095,21 +1102,21 @@ static const unsigned char twobyte_uses_ + /* 0 1 2 3 4 5 6 7 8 9 a b c d e f */ + /* ------------------------------- */ + /* 00 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* 0f */ +- /* 10 */ 1,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* 1f */ ++ /* 10 */ 1,1,1,0,0,0,1,0,0,0,0,0,0,0,0,0, /* 1f */ + /* 20 */ 0,0,0,0,0,0,0,0,0,0,1,0,1,1,0,0, /* 2f */ + /* 30 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* 3f */ + /* 40 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* 4f */ + /* 50 */ 0,1,1,1,0,0,0,0,1,1,1,1,1,1,1,1, /* 5f */ + /* 60 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,1, /* 6f */ +- /* 70 */ 1,0,0,0,0,0,0,0,0,0,0,0,0,0,1,1, /* 7f */ ++ /* 70 */ 1,0,0,0,0,0,0,0,0,0,0,0,1,1,1,1, /* 7f */ + /* 80 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* 8f */ + /* 90 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* 9f */ + /* a0 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* af */ + /* b0 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* bf */ + /* c0 */ 0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0, /* cf */ +- /* d0 */ 0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0, /* df */ ++ /* d0 */ 1,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0, /* df */ + /* e0 */ 0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0, /* ef */ +- /* f0 */ 0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0 /* ff */ ++ /* f0 */ 1,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0 /* ff */ + /* ------------------------------- */ + /* 0 1 2 3 4 5 6 7 8 9 a b c d e f */ + }; +@@ -1349,7 +1356,7 @@ static const struct dis386 grps[][8] = { + /* GRP7 */ + { + { "sgdtQ", M, XX, XX }, +- { "sidtQ", M, XX, XX }, ++ { "sidtQ", PNI_Fixup, 0, XX, XX }, + { "lgdtQ", M, XX, XX }, + { "lidtQ", M, XX, XX }, + { "smswQ", Ev, XX, XX }, +@@ -1638,6 +1645,48 @@ static const struct dis386 prefix_user_t + { "punpcklqdq", XM, EX, XX }, + { "(bad)", XM, EX, XX }, + }, ++ /* PREGRP27 */ ++ { ++ { "(bad)", MX, EX, XX }, ++ { "(bad)", XM, EX, XX }, ++ { "addsubpd", XM, EX, XX }, ++ { "addsubps", XM, EX, XX }, ++ }, ++ /* PREGRP28 */ ++ { ++ { "(bad)", MX, EX, XX }, ++ { "(bad)", XM, EX, XX }, ++ { "haddpd", XM, EX, XX }, ++ { "haddps", XM, EX, XX }, ++ }, ++ /* PREGRP29 */ ++ { ++ { "(bad)", MX, EX, XX }, ++ { "(bad)", XM, EX, XX }, ++ { "hsubpd", XM, EX, XX }, ++ { "hsubps", XM, EX, XX }, ++ }, ++ /* PREGRP30 */ ++ { ++ { "movlpX", XM, EX, SIMD_Fixup, 'h' }, /* really only 2 operands */ ++ { "movsldup", XM, EX, XX }, ++ { "movlpd", XM, EX, XX }, ++ { "movddup", XM, EX, XX }, ++ }, ++ /* PREGRP31 */ ++ { ++ { "movhpX", XM, EX, SIMD_Fixup, 'l' }, ++ { "movshdup", XM, EX, XX }, ++ { "movhpd", XM, EX, XX }, ++ { "(bad)", XM, EX, XX }, ++ }, ++ /* PREGRP32 */ ++ { ++ { "(bad)", XM, EX, XX }, ++ { "(bad)", XM, EX, XX }, ++ { "(bad)", XM, EX, XX }, ++ { "lddqu", XM, M, XX }, ++ }, + }; + + static const struct dis386 x86_64_table[][2] = { +@@ -2294,7 +2343,7 @@ static const char *float_mem[] = { + "fidivr{l||l|}", + /* db */ + "fild{l||l|}", +- "(bad)", ++ "fisttp{l||l|}", + "fist{l||l|}", + "fistp{l||l|}", + "(bad)", +@@ -2312,7 +2361,7 @@ static const char *float_mem[] = { + "fdivr{l||l|}", + /* dd */ + "fld{l||l|}", +- "(bad)", ++ "fisttpll", + "fst{l||l|}", + "fstp{l||l|}", + "frstor", +@@ -2330,7 +2379,7 @@ static const char *float_mem[] = { + "fidivr", + /* df */ + "fild", +- "(bad)", ++ "fisttp", + "fist", + "fistp", + "fbld", +@@ -4138,6 +4187,33 @@ SIMD_Fixup (extrachar, sizeflag) + } + + static void ++PNI_Fixup (extrachar, sizeflag) ++ int extrachar ATTRIBUTE_UNUSED; ++ int sizeflag ATTRIBUTE_UNUSED; ++{ ++ if (mod == 3 && reg == 1) ++ { ++ char *p = obuf + strlen (obuf); ++ ++ /* Override "sidt". */ ++ if (rm) ++ { ++ /* mwait %eax,%ecx */ ++ strcpy (p - 4, "mwait %eax,%ecx"); ++ } ++ else ++ { ++ /* monitor %eax,%ecx,%edx" */ ++ strcpy (p - 4, "monitor %eax,%ecx,%edx"); ++ } ++ ++ codep++; ++ } ++ else ++ OP_E (0, sizeflag); ++} ++ ++static void + BadOp (void) + { + /* Throw away prefixes and 1st. opcode byte. */ diff --git a/sys-devel/binutils/files/2.14/binutils-2.14.90.0.4-ppc-bigplt.patch b/sys-devel/binutils/files/2.14/binutils-2.14.90.0.4-ppc-bigplt.patch new file mode 100644 index 000000000000..2689ef78c390 --- /dev/null +++ b/sys-devel/binutils/files/2.14/binutils-2.14.90.0.4-ppc-bigplt.patch @@ -0,0 +1,16 @@ +2003-05-31 Jakub Jelinek <jakub@redhat.com> + + * elf32-ppc.c (allocate_dynrelocs): Use single slot for first 8192 + plt entries, not just 8191. + +--- bfd/elf32-ppc.c.jj 2003-05-30 11:19:17.000000000 -0400 ++++ bfd/elf32-ppc.c 2003-05-30 18:22:31.000000000 -0400 +@@ -2719,7 +2719,7 @@ allocate_dynrelocs (h, inf) + for two entries is allocated. */ + s->_raw_size += PLT_ENTRY_SIZE; + if ((s->_raw_size - PLT_INITIAL_ENTRY_SIZE) / PLT_ENTRY_SIZE +- >= PLT_NUM_SINGLE_ENTRIES) ++ > PLT_NUM_SINGLE_ENTRIES) + s->_raw_size += PLT_ENTRY_SIZE; + + /* We also need to make an entry in the .rela.plt section. */ diff --git a/sys-devel/binutils/files/2.14/binutils-2.14.90.0.4-ppc64-ctors.patch b/sys-devel/binutils/files/2.14/binutils-2.14.90.0.4-ppc64-ctors.patch new file mode 100644 index 000000000000..339fb690b5f0 --- /dev/null +++ b/sys-devel/binutils/files/2.14/binutils-2.14.90.0.4-ppc64-ctors.patch @@ -0,0 +1,20 @@ +2003-06-10 Alan Modra <amodra@bigpond.net.au> + + * emulparams/elf64ppc.sh (EXECUTABLE_SYMBOLS, OTHER_BSS_END_SYMBOLS, + CTOR_START, CTOR_END, DTOR_START, DTOR_END): Don't define. + +--- ld/emulparams/elf64ppc.sh 30 May 2003 15:50:11 -0000 ++++ ld/emulparams/elf64ppc.sh 10 Jun 2003 04:27:28 -0000 +@@ -12,12 +12,6 @@ COMMONPAGESIZE=0x1000 + ARCH=powerpc:common64 + MACHINE= + NOP=0x60000000 +-EXECUTABLE_SYMBOLS='PROVIDE (__stack = 0); PROVIDE (___stack = 0);' +-OTHER_BSS_END_SYMBOLS='__end = .;' +-CTOR_START='PROVIDE (__CTOR_LIST__ = .); PROVIDE (___CTOR_LIST__ = .);' +-CTOR_END='PROVIDE (__CTOR_END__ = .); PROVIDE (___CTOR_END__ = .);' +-DTOR_START='PROVIDE (__DTOR_LIST__ = .); PROVIDE (___DTOR_LIST__ = .);' +-DTOR_END='PROVIDE (__DTOR_END__ = .); PROVIDE (___DTOR_END__ = .);' + OTHER_TEXT_SECTIONS="*(.sfpr .glink)" + BSS_PLT= + OTHER_BSS_SYMBOLS=" diff --git a/sys-devel/binutils/files/2.14/binutils-2.14.90.0.4-ppc64-prelink.patch b/sys-devel/binutils/files/2.14/binutils-2.14.90.0.4-ppc64-prelink.patch new file mode 100644 index 000000000000..db21d8899ae4 --- /dev/null +++ b/sys-devel/binutils/files/2.14/binutils-2.14.90.0.4-ppc64-prelink.patch @@ -0,0 +1,132 @@ +2003-06-17 Alan Modra <amodra@bigpond.net.au> + + * elf64-ppc.c (ppc64_elf_relocate_section): Correct pcrel section zero. + +2003-06-16 Alan Modra <amodra@bigpond.net.au> + + * elf64-ppc.c (ppc64_elf_relocate_section): When optimizing toctprel + tls, check that a TOC16_DS or TOC16_LO_DS reloc isn't pointing to a + dtprel entry. Ensure TLS_LD DTPMOD reloc has a zero addend. Write + got section for RELATIVE relocs. Fix wrong comment. Change condition + under which dynamic relocs update the section contents. + +--- bfd/elf64-ppc.c 10 Jun 2003 07:44:09 -0000 1.101 ++++ bfd/elf64-ppc.c 16 Jun 2003 10:50:22 -0000 1.102 +@@ -7153,7 +7153,11 @@ ppc64_elf_relocate_section (output_bfd, + tls_mask = *toc_tls; + if (r_type == R_PPC64_TOC16_DS + || r_type == R_PPC64_TOC16_LO_DS) +- goto toctprel; ++ { ++ if (tls_mask != 0 ++ && (tls_mask & (TLS_DTPREL | TLS_TPREL)) == 0) ++ goto toctprel; ++ } + else + { + /* If we found a GD reloc pair, then we might be +@@ -7176,11 +7180,11 @@ ppc64_elf_relocate_section (output_bfd, + + case R_PPC64_GOT_TPREL16_DS: + case R_PPC64_GOT_TPREL16_LO_DS: +- toctprel: + if (tls_mask != 0 + && (tls_mask & TLS_TPREL) == 0) + { + bfd_vma insn; ++ toctprel: + insn = bfd_get_32 (output_bfd, contents + rel->r_offset - 2); + insn &= 31 << 21; + insn |= 0x3c0d0000; /* addis 0,13,0 */ +@@ -7653,6 +7657,7 @@ ppc64_elf_relocate_section (output_bfd, + outrel.r_offset = (htab->sgot->output_section->vma + + htab->sgot->output_offset + + off); ++ outrel.r_addend = rel->r_addend; + if (tls_type & (TLS_LD | TLS_GD)) + { + outrel.r_addend = 0; +@@ -7665,6 +7670,7 @@ ppc64_elf_relocate_section (output_bfd, + bfd_elf64_swap_reloca_out (output_bfd, + &outrel, loc); + outrel.r_offset += 8; ++ outrel.r_addend = rel->r_addend; + outrel.r_info + = ELF64_R_INFO (indx, R_PPC64_DTPREL64); + } +@@ -7674,11 +7680,18 @@ ppc64_elf_relocate_section (output_bfd, + else if (tls_type == (TLS_TLS | TLS_TPREL)) + outrel.r_info = ELF64_R_INFO (indx, R_PPC64_TPREL64); + else if (indx == 0) +- outrel.r_info = ELF64_R_INFO (indx, R_PPC64_RELATIVE); ++ { ++ outrel.r_info = ELF64_R_INFO (indx, R_PPC64_RELATIVE); ++ ++ /* Write the .got section contents for the sake ++ of prelink. */ ++ loc = htab->sgot->contents + off; ++ bfd_put_64 (output_bfd, outrel.r_addend + relocation, loc); ++ } + else + outrel.r_info = ELF64_R_INFO (indx, R_PPC64_GLOB_DAT); +- outrel.r_addend = rel->r_addend; +- if (indx == 0) ++ ++ if (indx == 0 && tls_type != (TLS_TLS | TLS_LD)) + { + outrel.r_addend += relocation; + if (tls_type & (TLS_GD | TLS_DTPREL | TLS_TPREL)) +@@ -7921,8 +7934,6 @@ ppc64_elf_relocate_section (output_bfd, + or this is an opd section reloc which must point + at a local function. */ + outrel.r_addend += relocation; +- /* ??? why? */ +- relocate = TRUE; + if (r_type == R_PPC64_ADDR64 || r_type == R_PPC64_TOC) + { + if (is_opd && h != NULL) +@@ -7940,6 +7951,12 @@ ppc64_elf_relocate_section (output_bfd, + unresolved_reloc = FALSE; + } + outrel.r_info = ELF64_R_INFO (0, R_PPC64_RELATIVE); ++ ++ /* We need to relocate .opd contents for ld.so. ++ Prelink also wants simple and consistent rules ++ for relocs. This make all RELATIVE relocs have ++ *r_offset equal to r_addend. */ ++ relocate = TRUE; + } + else + { +@@ -7981,9 +7998,29 @@ ppc64_elf_relocate_section (output_bfd, + + /* If this reloc is against an external symbol, it will + be computed at runtime, so there's no need to do +- anything now. */ ++ anything now. However, for the sake of prelink ensure ++ that the section contents are a known value. */ + if (! relocate) +- continue; ++ { ++ unresolved_reloc = FALSE; ++ /* The value chosen here is quite arbitrary as ld.so ++ ignores section contents except for the special ++ case of .opd where the contents might be accessed ++ before relocation. Choose zero, as that won't ++ cause reloc overflow. */ ++ relocation = 0; ++ addend = 0; ++ /* Use *r_offset == r_addend for R_PPC64_ADDR64 relocs ++ to improve backward compatibility with older ++ versions of ld. */ ++ if (r_type == R_PPC64_ADDR64) ++ addend = outrel.r_addend; ++ /* Adjust pc_relative relocs to have zero in *r_offset. */ ++ else if (ppc64_elf_howto_table[(int) r_type]->pc_relative) ++ addend = (input_section->output_section->vma ++ + input_section->output_offset ++ + rel->r_offset); ++ } + } + break; + diff --git a/sys-devel/binutils/files/2.14/binutils-2.14.90.0.4-pt-gnu-stack.patch b/sys-devel/binutils/files/2.14/binutils-2.14.90.0.4-pt-gnu-stack.patch new file mode 100644 index 000000000000..d6cfd392dc44 --- /dev/null +++ b/sys-devel/binutils/files/2.14/binutils-2.14.90.0.4-pt-gnu-stack.patch @@ -0,0 +1,235 @@ +2003-06-03 Jakub Jelinek <jakub@redhat.com> + +binutils/ + * readelf.c (get_segment_type): Handle PT_GNU_STACK. +bfd/ + * elf.c (_bfd_elf_print_private_bfd_data): Handle PT_GNU_STACK. + (bfd_section_from_phdr): Likewise. + (map_sections_to_segments): Create PT_GNU_STACK segment header. + (get_program_header_size): Count with PT_GNU_STACK. + * elf-bfd.h (struct elf_obj_tdata): Add stack_flags. + * elflink.h (bfd_elfNN_size_dynamic_sections): Set stack_flags. +include/ + * bfdlink.h (struct bfd_link_info): Add execstack and noexecstack. + * elf/common.h (PT_GNU_STACK): Define. +ld/ + * ldgram.y (phdr_type): Grok PT_GNU_STACK. + * emultempl/elf32.em (gld${EMULATION_NAME}_handle_option): Add + -z execstack and -z noexecstack. + (gld${EMULATION_NAME}_list_options): Likewise. + * scripttempl/elf.sc: If not -r, discard .note.GNU-stack section. + +--- binutils/readelf.c.jj 2003-05-23 09:24:40.000000000 -0400 ++++ binutils/readelf.c 2003-05-23 10:50:05.000000000 -0400 +@@ -2307,6 +2307,7 @@ get_segment_type (p_type) + + case PT_GNU_EH_FRAME: + return "GNU_EH_FRAME"; ++ case PT_GNU_STACK: return "STACK"; + + default: + if ((p_type >= PT_LOPROC) && (p_type <= PT_HIPROC)) +--- bfd/elf.c.jj 2003-05-23 09:24:39.000000000 -0400 ++++ bfd/elf.c 2003-05-23 16:15:02.000000000 -0400 +@@ -1070,6 +1070,7 @@ _bfd_elf_print_private_bfd_data (abfd, f + case PT_PHDR: pt = "PHDR"; break; + case PT_TLS: pt = "TLS"; break; + case PT_GNU_EH_FRAME: pt = "EH_FRAME"; break; ++ case PT_GNU_STACK: pt = "STACK"; break; + default: sprintf (buf, "0x%lx", p->p_type); pt = buf; break; + } + fprintf (f, "%8s off 0x", pt); +@@ -2296,6 +2297,9 @@ bfd_section_from_phdr (abfd, hdr, index) + return _bfd_elf_make_section_from_phdr (abfd, hdr, index, + "eh_frame_hdr"); + ++ case PT_GNU_STACK: ++ return _bfd_elf_make_section_from_phdr (abfd, hdr, index, "stack"); ++ + default: + /* Check for any processor-specific program segment types. + If no handler for them, default to making "segment" sections. */ +@@ -3513,6 +3517,21 @@ map_sections_to_segments (abfd) + pm = &m->next; + } + ++ if (elf_tdata (abfd)->stack_flags) ++ { ++ amt = sizeof (struct elf_segment_map); ++ m = (struct elf_segment_map *) bfd_zalloc (abfd, amt); ++ if (m == NULL) ++ goto error_return; ++ m->next = NULL; ++ m->p_type = PT_GNU_STACK; ++ m->p_flags = elf_tdata (abfd)->stack_flags; ++ m->p_flags_valid = 1; ++ ++ *pm = m; ++ pm = &m->next; ++ } ++ + free (sections); + sections = NULL; + +@@ -4099,6 +4118,12 @@ get_program_header_size (abfd) + ++segs; + } + ++ if (elf_tdata (abfd)->stack_flags) ++ { ++ /* We need a PT_GNU_STACK segment. */ ++ ++segs; ++ } ++ + for (s = abfd->sections; s != NULL; s = s->next) + { + if ((s->flags & SEC_LOAD) != 0 +--- bfd/elf-bfd.h.jj 2003-05-23 09:24:39.000000000 -0400 ++++ bfd/elf-bfd.h 2003-05-23 10:30:28.000000000 -0400 +@@ -1254,6 +1254,9 @@ struct elf_obj_tdata + /* Number of symbol version references we are about to emit. */ + unsigned int cverrefs; + ++ /* Segment flags for the PT_GNU_STACK segment. */ ++ unsigned int stack_flags; ++ + /* Symbol version definitions in external objects. */ + Elf_Internal_Verdef *verdef; + +--- bfd/elflink.h.jj 2003-05-23 09:24:40.000000000 -0400 ++++ bfd/elflink.h 2003-05-23 16:35:55.000000000 -0400 +@@ -1937,6 +1937,43 @@ NAME(bfd_elf,size_dynamic_sections) (out + if (! is_elf_hash_table (info)) + return TRUE; + ++ if (info->execstack) ++ elf_tdata (output_bfd)->stack_flags = PF_R | PF_W | PF_X; ++ else if (info->noexecstack) ++ elf_tdata (output_bfd)->stack_flags = PF_R | PF_W; ++ else ++ { ++ bfd *inputobj; ++ asection *notesec = NULL; ++ int exec = 0; ++ ++ for (inputobj = info->input_bfds; ++ inputobj; ++ inputobj = inputobj->link_next) ++ { ++ asection *s; ++ ++ if (inputobj->flags & DYNAMIC) ++ continue; ++ s = bfd_get_section_by_name (inputobj, ".note.GNU-stack"); ++ if (s) ++ { ++ if (s->flags & SEC_CODE) ++ exec = PF_X; ++ notesec = s; ++ } ++ else ++ exec = PF_X; ++ } ++ if (notesec) ++ { ++ elf_tdata (output_bfd)->stack_flags = PF_R | PF_W | exec; ++ if (exec && info->relocateable ++ && notesec->output_section != bfd_abs_section_ptr) ++ notesec->output_section->flags |= SEC_CODE; ++ } ++ } ++ + /* Any syms created from now on start with -1 in + got.refcount/offset and plt.refcount/offset. */ + elf_hash_table (info)->init_refcount = elf_hash_table (info)->init_offset; +--- include/bfdlink.h.jj 2003-05-23 09:24:43.000000000 -0400 ++++ include/bfdlink.h 2003-05-23 10:07:06.000000000 -0400 +@@ -291,6 +291,14 @@ struct bfd_link_info + /* TRUE if relaxation is being finalized. */ + unsigned int relax_finalizing: 1; + ++ /* TRUE if PT_GNU_STACK segment should be created with PF_R|PF_W|PF_X ++ flags. */ ++ unsigned int execstack: 1; ++ ++ /* TRUE if PT_GNU_STACK segment should be created with PF_R|PF_W ++ flags. */ ++ unsigned int noexecstack: 1; ++ + /* Which symbols to strip. */ + enum bfd_link_strip strip; + +--- include/elf/common.h.jj 2003-05-23 09:24:43.000000000 -0400 ++++ include/elf/common.h 2003-05-23 09:32:48.000000000 -0400 +@@ -288,6 +288,7 @@ + #define PT_HIPROC 0x7FFFFFFF /* Processor-specific */ + + #define PT_GNU_EH_FRAME (PT_LOOS + 0x474e550) ++#define PT_GNU_STACK (PT_LOOS + 0x474e551) + + /* Program segment permissions, in program header p_flags field. */ + +--- ld/ldgram.y.jj 2003-05-05 18:28:06.000000000 -0400 ++++ ld/ldgram.y 2003-05-23 16:52:09.000000000 -0400 +@@ -1006,6 +1006,8 @@ phdr_type: + { + if (strcmp (s, "PT_GNU_EH_FRAME") == 0) + $$ = exp_intop (0x6474e550); ++ else if (strcmp (s, "PT_GNU_STACK") == 0) ++ $$ = exp_intop (0x6474e551); + else + { + einfo (_("\ +--- ld/emultempl/elf32.em.jj 2003-05-19 17:12:46.000000000 -0400 ++++ ld/emultempl/elf32.em 2003-05-23 10:08:07.000000000 -0400 +@@ -1664,6 +1664,16 @@ cat >>e${EMULATION_NAME}.c <<EOF + link_info.combreloc = FALSE; + else if (strcmp (optarg, "nocopyreloc") == 0) + link_info.nocopyreloc = TRUE; ++ else if (strcmp (optarg, "execstack") == 0) ++ { ++ link_info.execstack = TRUE; ++ link_info.noexecstack = FALSE; ++ } ++ else if (strcmp (optarg, "noexecstack") == 0) ++ { ++ link_info.noexecstack = TRUE; ++ link_info.execstack = FALSE; ++ } + /* What about the other Solaris -z options? FIXME. */ + break; + EOF +@@ -1702,6 +1712,7 @@ cat >>e${EMULATION_NAME}.c <<EOF + fprintf (file, _(" --eh-frame-hdr\tCreate .eh_frame_hdr section\n")); + fprintf (file, _(" -z combreloc\t\tMerge dynamic relocs into one section and sort\n")); + fprintf (file, _(" -z defs\t\tDisallows undefined symbols\n")); ++ fprintf (file, _(" -z execstack\t\tMark executable as requiring executable stack\n")); + fprintf (file, _(" -z initfirst\t\tMark DSO to be initialized first at runtime\n")); + fprintf (file, _(" -z interpose\t\tMark object to interpose all DSOs but executable\n")); + fprintf (file, _(" -z loadfltr\t\tMark object requiring immediate process\n")); +@@ -1712,6 +1723,7 @@ cat >>e${EMULATION_NAME}.c <<EOF + fprintf (file, _(" -z nodelete\t\tMark DSO non-deletable at runtime\n")); + fprintf (file, _(" -z nodlopen\t\tMark DSO not available to dlopen\n")); + fprintf (file, _(" -z nodump\t\tMark DSO not available to dldump\n")); ++ fprintf (file, _(" -z noexecstack\t\tMark executable as not requiring executable stack\n")); + fprintf (file, _(" -z now\t\tMark object non-lazy runtime binding\n")); + fprintf (file, _(" -z origin\t\tMark object requiring immediate \$ORIGIN processing\n\t\t\t at runtime\n")); + fprintf (file, _(" -z KEYWORD\t\tIgnored for Solaris compatibility\n")); +--- ld/scripttempl/elf.sc.jj 2003-04-14 10:57:55.000000000 -0400 ++++ ld/scripttempl/elf.sc 2003-05-23 16:23:06.000000000 -0400 +@@ -84,6 +84,7 @@ INTERP=".interp ${RELOCATING-0} : + PLT=".plt ${RELOCATING-0} : { *(.plt) }" + DYNAMIC=".dynamic ${RELOCATING-0} : { *(.dynamic) }" + RODATA=".rodata ${RELOCATING-0} : { *(.rodata${RELOCATING+ .rodata.* .gnu.linkonce.r.*}) }" ++STACKNOTE="/DISCARD/ : { *(.note.GNU-stack) }" + if test -z "${NO_SMALL_DATA}"; then + SBSS=".sbss ${RELOCATING-0} : + { +@@ -395,5 +396,6 @@ cat <<EOF + ${STACK_ADDR+${STACK}} + ${OTHER_SECTIONS} + ${RELOCATING+${OTHER_END_SYMBOLS}} ++ ${RELOCATING+${STACKNOTE}} + } + EOF + diff --git a/sys-devel/binutils/files/2.14/binutils-2.14.90.0.4-sparc-nonpic.patch b/sys-devel/binutils/files/2.14/binutils-2.14.90.0.4-sparc-nonpic.patch new file mode 100644 index 000000000000..78b55fe1e398 --- /dev/null +++ b/sys-devel/binutils/files/2.14/binutils-2.14.90.0.4-sparc-nonpic.patch @@ -0,0 +1,94 @@ +2002-04-20 Jakub Jelinek <jakub@redhat.com> + + * elf32-sparc.c (elf32_sparc_relocate_section): Find real output + section with SEC_MERGE. + * elf64-sparc.c (sparc64_elf_relocate_section): Likewise. + +--- bfd/elf32-sparc.c.jj Thu Feb 6 08:07:10 2003 ++++ bfd/elf32-sparc.c Thu Feb 6 08:31:54 2003 +@@ -2168,7 +2168,7 @@ elf32_sparc_relocate_section (output_bfd + struct elf_link_hash_entry *h; + Elf_Internal_Sym *sym; + asection *sec; +- bfd_vma relocation, off; ++ bfd_vma relocation, off, orig_addend = 0; + bfd_reloc_status_type r; + bfd_boolean is_plt = FALSE; + bfd_boolean unresolved_reloc; +@@ -2196,6 +2196,7 @@ elf32_sparc_relocate_section (output_bfd + { + sym = local_syms + r_symndx; + sec = local_sections[r_symndx]; ++ orig_addend = rel->r_addend; + relocation = _bfd_elf_rela_local_sym (output_bfd, sym, sec, rel); + } + else +@@ -2525,6 +2526,24 @@ elf32_sparc_relocate_section (output_bfd + asection *osec; + + osec = sec->output_section; ++ /* FIXME: As soon as making sections zero size ++ is possible, this if can go away. */ ++ if (bfd_is_abs_section (osec) ++ && h == NULL ++ && (sec->flags & SEC_MERGE) ++ && ELF_ST_TYPE (sym->st_info) == STT_SECTION ++ && sec->sec_info_type == ELF_INFO_TYPE_MERGE) ++ { ++ asection *msec; ++ ++ msec = sec; ++ _bfd_merged_section_offset (output_bfd, &msec, ++ elf_section_data (sec)->sec_info, ++ sym->st_value + orig_addend, ++ (bfd_vma) 0); ++ osec = msec->output_section; ++ } ++ + indx = elf_section_data (osec)->dynindx; + + /* FIXME: we really should be able to link non-pic +--- bfd/elf64-sparc.c.jj Thu Feb 6 08:07:10 2003 ++++ bfd/elf64-sparc.c Thu Feb 6 08:31:54 2003 +@@ -2016,7 +2016,7 @@ sparc64_elf_relocate_section (output_bfd + struct elf_link_hash_entry *h; + Elf_Internal_Sym *sym; + asection *sec; +- bfd_vma relocation, off; ++ bfd_vma relocation, off, orig_addend = 0; + bfd_reloc_status_type r; + bfd_boolean is_plt = FALSE; + bfd_boolean unresolved_reloc; +@@ -2039,6 +2039,7 @@ sparc64_elf_relocate_section (output_bfd + { + sym = local_syms + r_symndx; + sec = local_sections[r_symndx]; ++ orig_addend = rel->r_addend; + relocation = _bfd_elf_rela_local_sym (output_bfd, sym, sec, rel); + } + else +@@ -2267,6 +2268,24 @@ sparc64_elf_relocate_section (output_bfd + asection *osec; + + osec = sec->output_section; ++ /* FIXME: As soon as making sections zero size ++ is possible, this if can go away. */ ++ if (bfd_is_abs_section (osec) ++ && h == NULL ++ && (sec->flags & SEC_MERGE) ++ && ELF_ST_TYPE (sym->st_info) == STT_SECTION ++ && sec->sec_info_type == ELF_INFO_TYPE_MERGE) ++ { ++ asection *msec; ++ ++ msec = sec; ++ _bfd_merged_section_offset (output_bfd, &msec, ++ elf_section_data (sec)->sec_info, ++ sym->st_value + orig_addend, ++ (bfd_vma) 0); ++ osec = msec->output_section; ++ } ++ + indx = elf_section_data (osec)->dynindx; + + /* We are turning this relocation into one diff --git a/sys-devel/binutils/files/digest-binutils-2.14.90.0.4.1-r1 b/sys-devel/binutils/files/digest-binutils-2.14.90.0.4.1-r1 new file mode 100644 index 000000000000..4d12da56df02 --- /dev/null +++ b/sys-devel/binutils/files/digest-binutils-2.14.90.0.4.1-r1 @@ -0,0 +1 @@ +MD5 e4907bd263ef912096ec8c0f64033a9b binutils-2.14.90.0.4.1.tar.bz2 10436800 |