diff options
author | Richard Henderson <rth@redhat.com> | 2011-12-14 19:24:05 -0800 |
---|---|---|
committer | Richard Henderson <rth@gcc.gnu.org> | 2011-12-14 19:24:05 -0800 |
commit | aebac0ca061219f37518e6804e1b6319e68c0979 (patch) | |
tree | d69d530d9b08693c960ebf681af1cb7de90883dc /libitm/config/arm | |
parent | cc50a1e14ed07a9f2031809aa9225dc6739267ab (diff) | |
download | gcc-aebac0ca061219f37518e6804e1b6319e68c0979.zip gcc-aebac0ca061219f37518e6804e1b6319e68c0979.tar.gz gcc-aebac0ca061219f37518e6804e1b6319e68c0979.tar.bz2 |
arm-linux: Add libitm support.
* config/arm/hwcap.h, config/arm/hwcap.cc: New files.
* config/arm/sjlj.S, config/arm/target.h: New files.
* config/generic/asmcfi.h (cfi_adjust_cfa_offset): New.
(cfi_rel_offset): New.
* config/linux/futex_bits.h: New file.
* config/linux/futex.cc: Include futex_bits.h here...
* config/linux/futex.h: ... not here.
* Makefile.am (libitm_la_SOURCES) <ARCH_ARM>: Add hwcap.cc.
* configure.ac (ARCH_AM): New conditional.
* Makefile.in, configure: Rebuild.
* configure.tgt: Handle ARM.
From-SVN: r182355
Diffstat (limited to 'libitm/config/arm')
-rw-r--r-- | libitm/config/arm/hwcap.cc | 67 | ||||
-rw-r--r-- | libitm/config/arm/hwcap.h | 41 | ||||
-rw-r--r-- | libitm/config/arm/sjlj.S | 164 | ||||
-rw-r--r-- | libitm/config/arm/target.h | 53 |
4 files changed, 325 insertions, 0 deletions
diff --git a/libitm/config/arm/hwcap.cc b/libitm/config/arm/hwcap.cc new file mode 100644 index 0000000..007c10e --- /dev/null +++ b/libitm/config/arm/hwcap.cc @@ -0,0 +1,67 @@ +/* Copyright (C) 2011 Free Software Foundation, Inc. + Contributed by Richard Henderson <rth@redhat.com>. + + This file is part of the GNU Transactional Memory Library (libitm). + + Libitm is free software; you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by + the Free Software Foundation; either version 3 of the License, or + (at your option) any later version. + + Libitm is distributed in the hope that it will be useful, but WITHOUT ANY + WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS + FOR A PARTICULAR PURPOSE. See the GNU General Public License for + more details. + + Under Section 7 of GPL version 3, you are granted additional + permissions described in the GCC Runtime Library Exception, version + 3.1, as published by the Free Software Foundation. + + You should have received a copy of the GNU General Public License and + a copy of the GCC Runtime Library Exception along with this program; + see the files COPYING3 and COPYING.RUNTIME respectively. If not, see + <http://www.gnu.org/licenses/>. */ + +/* This file initializes GTM_hwcap in some os-specific way to indicate + what ISA extensions are present for ARM. */ + +#include "libitm_i.h" +#include "hwcap.h" + +/* Begin by defaulting to whatever options were given to the compiler. */ +int GTM_hwcap HIDDEN = 0 +#ifdef __VFP_FP__ + | HWCAP_ARM_VFP +#endif +#ifdef __IWMMXT__ + | HWCAP_ARM_IWMMXT +#endif + ; + +#ifdef __linux__ +#include <unistd.h> +#include <sys/fcntl.h> +#include <elf.h> + +static void __attribute__((constructor)) +init_gtm_hwcap(void) +{ + int fd = open ("/proc/self/auxv", O_RDONLY); + if (fd < 0) + return; + + Elf32_auxv_t pairs[512]; + ssize_t rlen = read (fd, pairs, sizeof(pairs)); + close (fd); + if (rlen < 0) + return; + + size_t n = (size_t)rlen / sizeof(pairs[0]); + for (size_t i = 0; i < n; ++i) + if (pairs[i].a_type == AT_HWCAP) + { + GTM_hwcap = pairs[i].a_un.a_val; + return; + } +} +#endif diff --git a/libitm/config/arm/hwcap.h b/libitm/config/arm/hwcap.h new file mode 100644 index 0000000..16e4034 --- /dev/null +++ b/libitm/config/arm/hwcap.h @@ -0,0 +1,41 @@ +/* Copyright (C) 2011 Free Software Foundation, Inc. + Contributed by Richard Henderson <rth@redhat.com>. + + This file is part of the GNU Transactional Memory Library (libitm). + + Libitm is free software; you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by + the Free Software Foundation; either version 3 of the License, or + (at your option) any later version. + + Libitm is distributed in the hope that it will be useful, but WITHOUT ANY + WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS + FOR A PARTICULAR PURPOSE. See the GNU General Public License for + more details. + + Under Section 7 of GPL version 3, you are granted additional + permissions described in the GCC Runtime Library Exception, version + 3.1, as published by the Free Software Foundation. + + You should have received a copy of the GNU General Public License and + a copy of the GCC Runtime Library Exception along with this program; + see the files COPYING3 and COPYING.RUNTIME respectively. If not, see + <http://www.gnu.org/licenses/>. */ + +/* The following must match the kernel's <asm/procinfo.h>. */ +#define HWCAP_ARM_SWP 1 +#define HWCAP_ARM_HALF 2 +#define HWCAP_ARM_THUMB 4 +#define HWCAP_ARM_26BIT 8 +#define HWCAP_ARM_FAST_MULT 16 +#define HWCAP_ARM_FPA 32 +#define HWCAP_ARM_VFP 64 +#define HWCAP_ARM_EDSP 128 +#define HWCAP_ARM_JAVA 256 +#define HWCAP_ARM_IWMMXT 512 +#define HWCAP_ARM_CRUNCH 1024 +#define HWCAP_ARM_THUMBEE 2048 +#define HWCAP_ARM_NEON 4096 +#define HWCAP_ARM_VFPv3 8192 +#define HWCAP_ARM_VFPv3D16 16384 + diff --git a/libitm/config/arm/sjlj.S b/libitm/config/arm/sjlj.S new file mode 100644 index 0000000..2c9fb02 --- /dev/null +++ b/libitm/config/arm/sjlj.S @@ -0,0 +1,164 @@ +/* Copyright (C) 2011 Free Software Foundation, Inc. + Contributed by Richard Henderson <rth@redhat.com>. + + This file is part of the GNU Transactional Memory Library (libitm). + + Libitm is free software; you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by + the Free Software Foundation; either version 3 of the License, or + (at your option) any later version. + + Libitm is distributed in the hope that it will be useful, but WITHOUT ANY + WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS + FOR A PARTICULAR PURPOSE. See the GNU General Public License for + more details. + + Under Section 7 of GPL version 3, you are granted additional + permissions described in the GCC Runtime Library Exception, version + 3.1, as published by the Free Software Foundation. + + You should have received a copy of the GNU General Public License and + a copy of the GCC Runtime Library Exception along with this program; + see the files COPYING3 and COPYING.RUNTIME respectively. If not, see + <http://www.gnu.org/licenses/>. */ + +#include "hwcap.h" +#include "asmcfi.h" + + .syntax unified + +#if defined(__thumb2__) +# define PC_OFS 4 + .thumb + .thumb_func +#else +# define PC_OFS 8 +#endif + +#if defined (__thumb2__) && defined(__ARM_ARCH_6T2__) +# define HAVE_MOVT + .arch armv6t2 +#elif defined (__ARM_ARCH_7A__) +# define HAVE_MOVT + .arch armv7-a +#elif defined (__ARM_ARCH_7R__) +# define HAVE_MOVT + .arch armv7-r +#elif defined (__ARM_ARCH_7M__) +# define HAVE_MOVT + .arch armv7-m +#endif + +#if defined(HAVE_MOVT) && defined(PIC) +.macro ldaddr reg, addr + movw \reg, #:lower16:(\addr - (98f + PC_OFS)) + movt \reg, #:upper16:(\addr - (98f + PC_OFS)) +98: add \reg, \reg, pc +.endm +#elif defined(HAVE_MOVT) +.macro ldaddr reg, addr + movw \reg, #:lower16:\addr + movt \reg, #:upper16:\addr +.endm +#elif defined(PIC) +.macro ldaddr reg, addr + ldr \reg, 99f +98: add \reg, \reg, pc +.subsection 1 + .align 2 +99: .word \addr - (98b + PC_OFS) +.subsection 0 +.endm +#else +.macro ldaddr reg, addr + ldr \reg, =\addr +.endm +#endif + + .text + .align 2 + .global _ITM_beginTransaction + .type _ITM_beginTransaction, %function + +_ITM_beginTransaction: + .fnstart + cfi_startproc + mov ip, sp + push { r4-r11, ip, lr } + .save { lr } + .pad #(9*4) + cfi_adjust_cfa_offset(40) + cfi_rel_offset(lr, 36) + sub sp, sp, #(14*8) + .pad #(14*8) + cfi_adjust_cfa_offset(14*8) + + ldaddr r2, GTM_hwcap + ldr r2, [r2] + + /* Store the VFP registers. Don't use VFP instructions directly + because this code is used in non-VFP multilibs. */ + tst r2, #HWCAP_ARM_VFP + beq 1f + stc p11, cr8, [sp], {16} /* vstm sp, {d8-d15} */ +1: + /* Save the call-preserved iWMMXt registers. */ + tst r2, #HWCAP_ARM_IWMMXT + beq 1f + stcl p1, cr10, [sp, #64] /* wstrd wr10, [sp, #64] */ + stcl p1, cr11, [sp, #72] + stcl p1, cr12, [sp, #80] + stcl p1, cr13, [sp, #88] + stcl p1, cr14, [sp, #96] + stcl p1, cr15, [sp, #104] +1: + /* Invoke GTM_begin_transaction with the struct we just built. */ + mov r1, sp + bl GTM_begin_transaction + + /* Return; we don't need to restore any of the call-saved regs. */ + add sp, sp, #(14*8 + 9*4) + cfi_adjust_cfa_offset(-(14*8 + 9*4)) + pop { pc } + .fnend + cfi_endproc + .size _ITM_beginTransaction, . - _ITM_beginTransaction + + .align 2 + .global GTM_longjmp + .hidden GTM_longjmp + .type GTM_longjmp, %function + +GTM_longjmp: + cfi_startproc + ldaddr r2, GTM_hwcap + ldr r2, [r2] + + tst r2, #HWCAP_ARM_VFP + beq 1f + ldc p11, cr8, [r1], {16} /* vldmia r1, {d8-d15} */ +1: + tst r2, #HWCAP_ARM_IWMMXT + beq 1f + ldcl p1, cr10, [r1, #64] /* wldrd wr10, [r1, #64] */ + ldcl p1, cr11, [r1, #72] + ldcl p1, cr12, [r1, #80] + ldcl p1, cr13, [r1, #88] + ldcl p1, cr14, [r1, #96] + ldcl p1, cr15, [r1, #104] +1: + add r1, r1, #(14*8) /* Skip both VFP and iWMMXt blocks */ +#ifdef __thumb2__ + ldm r1, { r4-r11, ip, lr } + cfi_def_cfa(ip, 0) + mov sp, ip + bx lr +#else + ldm r1, { r4-r11, sp, pc } +#endif + cfi_endproc + .size GTM_longjmp, . - GTM_longjmp + +#ifdef __linux__ +.section .note.GNU-stack, "", %progbits +#endif diff --git a/libitm/config/arm/target.h b/libitm/config/arm/target.h new file mode 100644 index 0000000..758d449 --- /dev/null +++ b/libitm/config/arm/target.h @@ -0,0 +1,53 @@ +/* Copyright (C) 2011 Free Software Foundation, Inc. + Contributed by Richard Henderson <rth@redhat.com>. + + This file is part of the GNU Transactional Memory Library (libitm). + + Libitm is free software; you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by + the Free Software Foundation; either version 3 of the License, or + (at your option) any later version. + + Libitm is distributed in the hope that it will be useful, but WITHOUT ANY + WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS + FOR A PARTICULAR PURPOSE. See the GNU General Public License for + more details. + + Under Section 7 of GPL version 3, you are granted additional + permissions described in the GCC Runtime Library Exception, version + 3.1, as published by the Free Software Foundation. + + You should have received a copy of the GNU General Public License and + a copy of the GCC Runtime Library Exception along with this program; + see the files COPYING3 and COPYING.RUNTIME respectively. If not, see + <http://www.gnu.org/licenses/>. */ + +namespace GTM HIDDEN { + +typedef struct gtm_jmpbuf +{ + unsigned long long vfp[8]; /* d8-d15 */ + unsigned long long iwmmxt[6]; /* cr10-cr15 */ + unsigned long gr[8]; /* r4-r11 */ + void *cfa; + unsigned long pc; +} gtm_jmpbuf; + +/* ARM generally uses a fixed page size of 4K. */ +#define PAGE_SIZE 4096 +#define FIXED_PAGE_SIZE 1 + +/* ??? The size of one line in hardware caches (in bytes). */ +#define HW_CACHELINE_SIZE 64 + +static inline void +cpu_relax (void) +{ + /* ??? The kernel uses the condition + #if __LINUX_ARM_ARCH__ == 6 || defined(CONFIG_ARM_ERRATA_754327) + Given that we're actually just waiting, it doesn't seem like it + hurts to simply use a full barrier all the time. */ + __sync_synchronize (); +} + +} // namespace GTM |