From patchwork Wed Aug 22 14:41:41 2012 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: "H.J. Lu" X-Patchwork-Id: 179330 Return-Path: X-Original-To: incoming@patchwork.ozlabs.org Delivered-To: patchwork-incoming@bilbo.ozlabs.org Received: from sourceware.org (server1.sourceware.org [209.132.180.131]) by ozlabs.org (Postfix) with SMTP id 2318D2C008B for ; Thu, 23 Aug 2012 00:43:12 +1000 (EST) Comment: DKIM? See http://www.dkim.org DKIM-Signature: v=1; a=rsa-sha1; c=relaxed/relaxed; d=gcc.gnu.org; s=default; x=1346251394; h=Comment: DomainKey-Signature:Received:Received:Received:Received:Received: Received:Date:From:To:Cc:Subject:Message-ID:Reply-To: MIME-Version:Content-Type:Content-Disposition:User-Agent: Mailing-List:Precedence:List-Id:List-Unsubscribe:List-Archive: List-Post:List-Help:Sender:Delivered-To; bh=onIUZozHB1xehqP20PxP 9C6Q/2k=; b=vpazNGidnw9JE3Cj7zUtDs0udE9ecrvTluH7KRscCcvqP589gEIf rxZfV0vb6YL/AJE+FZlM7YhVkmsBIgacMCckximavth8F4dGvvWrJNCLkNVv6qhb Vey7wjclM3hzhbpJwSipDKPgasnvAEm5xBAllZOvuPQD0INNPrAPv6w= Comment: DomainKeys? See http://antispam.yahoo.com/domainkeys DomainKey-Signature: a=rsa-sha1; q=dns; c=nofws; s=default; d=gcc.gnu.org; h=Received:Received:X-SWARE-Spam-Status:X-Spam-Check-By:Received:Received:X-ExtLoop1:Received:Received:Date:From:To:Cc:Subject:Message-ID:Reply-To:MIME-Version:Content-Type:Content-Disposition:User-Agent:Mailing-List:Precedence:List-Id:List-Unsubscribe:List-Archive:List-Post:List-Help:Sender:Delivered-To; b=BBMPIoEkch+m4AE+MNJC8SJ2NiZgkiaOWhdTl0eHf5KBzpt4kUgRwOquL+8P0V mVhiIIrYZ484/xy/X85HATFr33OWGc6IhkGL6dWkeLKfVuVwHnHiXnNEh0RTraL2 hiGQLrB1+B5ih0pXEopz2gPPd2A3OvZD9rhZAz9E8L+Zo=; Received: (qmail 22183 invoked by alias); 22 Aug 2012 14:42:31 -0000 Received: (qmail 21740 invoked by uid 22791); 22 Aug 2012 14:42:20 -0000 X-SWARE-Spam-Status: No, hits=-5.2 required=5.0 tests=AWL, BAYES_00, KHOP_RCVD_UNTRUST, NO_DNS_FOR_FROM, RCVD_IN_DNSWL_HI, RCVD_IN_HOSTKARMA_W, RP_MATCHES_RCVD X-Spam-Check-By: sourceware.org Received: from mga11.intel.com (HELO mga11.intel.com) (192.55.52.93) by sourceware.org (qpsmtpd/0.43rc1) with ESMTP; Wed, 22 Aug 2012 14:41:43 +0000 Received: from fmsmga001.fm.intel.com ([10.253.24.23]) by fmsmga102.fm.intel.com with ESMTP; 22 Aug 2012 07:41:42 -0700 X-ExtLoop1: 1 Received: from gnu-6.sc.intel.com ([10.3.194.135]) by fmsmga001.fm.intel.com with ESMTP; 22 Aug 2012 07:41:42 -0700 Received: by gnu-6.sc.intel.com (Postfix, from userid 500) id F37AD80CCF; Wed, 22 Aug 2012 07:41:41 -0700 (PDT) Date: Wed, 22 Aug 2012 07:41:41 -0700 From: "H.J. Lu" To: gcc-patches@gcc.gnu.org Cc: Uros Bizjak , Maxim Kuvyrkov Subject: PATCH: Default to 64-bit long double for Bionic/x86 Message-ID: <20120822144141.GA6489@intel.com> Reply-To: "H.J. Lu" MIME-Version: 1.0 Content-Disposition: inline User-Agent: Mutt/1.5.21 (2010-09-15) Mailing-List: contact gcc-patches-help@gcc.gnu.org; run by ezmlm Precedence: bulk List-Id: List-Unsubscribe: List-Archive: List-Post: List-Help: Sender: gcc-patches-owner@gcc.gnu.org Delivered-To: mailing list gcc-patches@gcc.gnu.org Hi, Long double is the same as double in Bionic. This patch 1. Add -mlong-double-80: 80-bit long double Enabled for Linux by default. 2. Add -mlong-double-64: 64-bit long double Predefine a new C/C++ macro, __LONG_DOUBLE_64__. Enabled for Android by default. __float80 can still be used for 80-bit long double. Tested on Linux/x86 and Android/x86. OK to install? Thanks. H.J. ---- gcc/ 2012-08-22 H.J. Lu * doc/invoke.texi: Document -mlong-double-64/-mlong-double-80. * config/i386/i386.c (flag_opts): Add -mlong-double-64. (TARGET_HAS_BIONIC): Default long double to 64-bit for Bionic. * config/i386/i386.h (LONG_DOUBLE_TYPE_SIZE): Use 64 if TARGET_LONG_DOUBLE_64 is true. (LIBGCC2_LONG_DOUBLE_TYPE_SIZE): New macro. (WIDEST_HARDWARE_FP_SIZE): Defined to 80. * config/i386/i386.opt (mlong-double-80): New option. (mlong-double-64): Likewise. * config/i386/i386-c.c (ix86_target_macros): Define __LONG_DOUBLE_64__ for TARGET_LONG_DOUBLE_64. gcc/testsuite/ 2012-08-22 H.J. Lu * gcc.target/i386/long-double-64-1.c: New file. * gcc.target/i386/long-double-64-2.c: Likewise. * gcc.target/i386/long-double-64-3.c: Likewise. * gcc.target/i386/long-double-64-4.c: Likewise. * gcc.target/i386/long-double-80-1.c: Likewise. * gcc.target/i386/long-double-80-2.c: Likewise. * gcc.target/i386/long-double-80-3.c: Likewise. * gcc.target/i386/long-double-80-4.c: Likewise. * gcc.target/i386/long-double-80-5.c: Likewise. * gcc.target/i386/long-double-80-6.c: Likewise. * gcc.target/i386/long-double-80-7.c: Likewise. libgcc/ 2012-08-22 H.J. Lu * config/i386/t-linux (HOST_LIBGCC2_CFLAGS): New. diff --git a/gcc/config/i386/i386-c.c b/gcc/config/i386/i386-c.c index d00e0ba..edd64ff 100644 --- a/gcc/config/i386/i386-c.c +++ b/gcc/config/i386/i386-c.c @@ -409,6 +409,9 @@ ix86_target_macros (void) builtin_define_std ("i386"); } + if (TARGET_LONG_DOUBLE_64) + cpp_define (parse_in, "__LONG_DOUBLE_64__"); + cpp_define_formatted (parse_in, "__ATOMIC_HLE_ACQUIRE=%d", IX86_HLE_ACQUIRE); cpp_define_formatted (parse_in, "__ATOMIC_HLE_RELEASE=%d", IX86_HLE_RELEASE); diff --git a/gcc/config/i386/i386.c b/gcc/config/i386/i386.c index a6fc45b..da931ee 100644 --- a/gcc/config/i386/i386.c +++ b/gcc/config/i386/i386.c @@ -2786,6 +2786,7 @@ ix86_target_string (HOST_WIDE_INT isa, int flags, const char *arch, static struct ix86_target_opts flag_opts[] = { { "-m128bit-long-double", MASK_128BIT_LONG_DOUBLE }, + { "-mlong-double-64", MASK_LONG_DOUBLE_64 }, { "-m80387", MASK_80387 }, { "-maccumulate-outgoing-args", MASK_ACCUMULATE_OUTGOING_ARGS }, { "-malign-double", MASK_ALIGN_DOUBLE }, @@ -4084,6 +4085,11 @@ ix86_option_override_internal (bool main_args_p) else if (target_flags_explicit & MASK_RECIP) recip_mask &= ~(RECIP_MASK_ALL & ~recip_mask_explicit); + /* Default long double to 64-bit for Bionic. */ + if (TARGET_HAS_BIONIC + && !(target_flags_explicit & MASK_LONG_DOUBLE_64)) + target_flags |= MASK_LONG_DOUBLE_64; + /* Save the initial options in case the user does function specific options. */ if (main_args_p) diff --git a/gcc/config/i386/i386.h b/gcc/config/i386/i386.h index 11f79e3..3a41a43 100644 --- a/gcc/config/i386/i386.h +++ b/gcc/config/i386/i386.h @@ -671,9 +671,17 @@ enum target_cpu_default #define LONG_LONG_TYPE_SIZE 64 #define FLOAT_TYPE_SIZE 32 #define DOUBLE_TYPE_SIZE 64 -#define LONG_DOUBLE_TYPE_SIZE 80 +#define LONG_DOUBLE_TYPE_SIZE (TARGET_LONG_DOUBLE_64 ? 64 : 80) -#define WIDEST_HARDWARE_FP_SIZE LONG_DOUBLE_TYPE_SIZE +/* Define this to set long double type size to use in libgcc2.c, which can + not depend on target_flags. */ +#ifdef __LONG_DOUBLE_64__ +#define LIBGCC2_LONG_DOUBLE_TYPE_SIZE 64 +#else +#define LIBGCC2_LONG_DOUBLE_TYPE_SIZE 80 +#endif + +#define WIDEST_HARDWARE_FP_SIZE 80 #if defined (TARGET_BI_ARCH) || TARGET_64BIT_DEFAULT #define MAX_BITS_PER_WORD 64 diff --git a/gcc/config/i386/i386.opt b/gcc/config/i386/i386.opt index e4f78f3..6a38994 100644 --- a/gcc/config/i386/i386.opt +++ b/gcc/config/i386/i386.opt @@ -86,6 +86,14 @@ m96bit-long-double Target RejectNegative Report InverseMask(128BIT_LONG_DOUBLE) Save sizeof(long double) is 12 +mlong-double-80 +Target Report RejectNegative InverseMask(LONG_DOUBLE_64) Save +Use 80-bit long double + +mlong-double-64 +Target Report RejectNegative Mask(LONG_DOUBLE_64) Save +Use 64-bit long double + maccumulate-outgoing-args Target Report Mask(ACCUMULATE_OUTGOING_ARGS) Save Reserve space for outgoing arguments in the function prologue diff --git a/gcc/doc/invoke.texi b/gcc/doc/invoke.texi index ae22ca9..0957979 100644 --- a/gcc/doc/invoke.texi +++ b/gcc/doc/invoke.texi @@ -636,7 +636,8 @@ Objective-C and Objective-C++ Dialects}. -mno-align-stringops -minline-all-stringops @gol -minline-stringops-dynamically -mstringop-strategy=@var{alg} @gol -mpush-args -maccumulate-outgoing-args -m128bit-long-double @gol --m96bit-long-double -mregparm=@var{num} -msseregparm @gol +-m96bit-long-double -mlong-double-64 -mlong-double-80 @gol +-mregparm=@var{num} -msseregparm @gol -mveclibabi=@var{type} -mvect8-ret-in-mem @gol -mpc32 -mpc64 -mpc80 -mstackrealign @gol -momit-leaf-frame-pointer -mno-red-zone -mno-tls-direct-seg-refs @gol @@ -13509,6 +13510,21 @@ as well as modifying the function calling convention for functions taking @code{long double}. Hence they are not binary-compatible with code compiled without that switch. +@item -mlong-double-64 +@itemx -mlong-double-80 +@opindex mlong-double-64 +@opindex mlong-double-80 +These switches control the size of @code{long double} type. A size +of 64 bits makes the @code{long double} type equivalent to the @code{double} +type. This is the default for Bionic C library. + +@strong{Warning:} if you override the default value for your target ABI, this +changes the size of +structures and arrays containing @code{long double} variables, +as well as modifying the function calling convention for functions taking +@code{long double}. Hence they are not binary-compatible +with code compiled without that switch. + @item -mlarge-data-threshold=@var{threshold} @opindex mlarge-data-threshold When @option{-mcmodel=medium} is specified, data objects larger than diff --git a/gcc/testsuite/gcc.target/i386/long-double-64-1.c b/gcc/testsuite/gcc.target/i386/long-double-64-1.c new file mode 100644 index 0000000..cf93379 --- /dev/null +++ b/gcc/testsuite/gcc.target/i386/long-double-64-1.c @@ -0,0 +1,10 @@ +/* { dg-do compile } */ +/* { dg-options "-O2 -mlong-double-64" } */ + +long double +foo (long double x) +{ + return x * x; +} + +/* { dg-final { scan-assembler-not "fldt" } } */ diff --git a/gcc/testsuite/gcc.target/i386/long-double-64-2.c b/gcc/testsuite/gcc.target/i386/long-double-64-2.c new file mode 100644 index 0000000..ddf4fe6 --- /dev/null +++ b/gcc/testsuite/gcc.target/i386/long-double-64-2.c @@ -0,0 +1,10 @@ +/* { dg-do compile { target *-*-linux* } } */ +/* { dg-options "-O2 -mbionic" } */ + +long double +foo (long double x) +{ + return x * x; +} + +/* { dg-final { scan-assembler-not "fldt" } } */ diff --git a/gcc/testsuite/gcc.target/i386/long-double-64-3.c b/gcc/testsuite/gcc.target/i386/long-double-64-3.c new file mode 100644 index 0000000..e748fab --- /dev/null +++ b/gcc/testsuite/gcc.target/i386/long-double-64-3.c @@ -0,0 +1,10 @@ +/* { dg-do compile { target *-*-linux* } } */ +/* { dg-options "-O2 -mandroid" } */ + +long double +foo (long double x) +{ + return x * x; +} + +/* { dg-final { scan-assembler-not "fldt" } } */ diff --git a/gcc/testsuite/gcc.target/i386/long-double-64-4.c b/gcc/testsuite/gcc.target/i386/long-double-64-4.c new file mode 100644 index 0000000..d9c25aa --- /dev/null +++ b/gcc/testsuite/gcc.target/i386/long-double-64-4.c @@ -0,0 +1,10 @@ +/* { dg-do compile } */ +/* { dg-options "-O2 -mlong-double-80 -mlong-double-64" } */ + +long double +foo (long double x) +{ + return x * x; +} + +/* { dg-final { scan-assembler-not "fldt" } } */ diff --git a/gcc/testsuite/gcc.target/i386/long-double-80-1.c b/gcc/testsuite/gcc.target/i386/long-double-80-1.c new file mode 100644 index 0000000..d3b75a0 --- /dev/null +++ b/gcc/testsuite/gcc.target/i386/long-double-80-1.c @@ -0,0 +1,10 @@ +/* { dg-do compile } */ +/* { dg-options "-O2 -mlong-double-80" } */ + +long double +foo (long double x) +{ + return x * x; +} + +/* { dg-final { scan-assembler "fldt" } } */ diff --git a/gcc/testsuite/gcc.target/i386/long-double-80-2.c b/gcc/testsuite/gcc.target/i386/long-double-80-2.c new file mode 100644 index 0000000..954dfd1 --- /dev/null +++ b/gcc/testsuite/gcc.target/i386/long-double-80-2.c @@ -0,0 +1,10 @@ +/* { dg-do compile { target *-*-linux* } } */ +/* { dg-options "-O2 -mlong-double-80 -mbionic" } */ + +long double +foo (long double x) +{ + return x * x; +} + +/* { dg-final { scan-assembler "fldt" } } */ diff --git a/gcc/testsuite/gcc.target/i386/long-double-80-3.c b/gcc/testsuite/gcc.target/i386/long-double-80-3.c new file mode 100644 index 0000000..e0e8365 --- /dev/null +++ b/gcc/testsuite/gcc.target/i386/long-double-80-3.c @@ -0,0 +1,10 @@ +/* { dg-do compile { target *-*-linux* } } */ +/* { dg-options "-O2 -mlong-double-80 -mandroid" } */ + +long double +foo (long double x) +{ + return x * x; +} + +/* { dg-final { scan-assembler "fldt" } } */ diff --git a/gcc/testsuite/gcc.target/i386/long-double-80-4.c b/gcc/testsuite/gcc.target/i386/long-double-80-4.c new file mode 100644 index 0000000..cac2d55 --- /dev/null +++ b/gcc/testsuite/gcc.target/i386/long-double-80-4.c @@ -0,0 +1,10 @@ +/* { dg-do compile } */ +/* { dg-options "-O2 -mlong-double-64 -mlong-double-80" } */ + +long double +foo (long double x) +{ + return x * x; +} + +/* { dg-final { scan-assembler "fldt" } } */ diff --git a/gcc/testsuite/gcc.target/i386/long-double-80-5.c b/gcc/testsuite/gcc.target/i386/long-double-80-5.c new file mode 100644 index 0000000..4aa606f --- /dev/null +++ b/gcc/testsuite/gcc.target/i386/long-double-80-5.c @@ -0,0 +1,10 @@ +/* { dg-do compile } */ +/* { dg-options "-O2 -mlong-double-64" } */ + +__float80 +foo (__float80 x) +{ + return x * x; +} + +/* { dg-final { scan-assembler "fldt" } } */ diff --git a/gcc/testsuite/gcc.target/i386/long-double-80-6.c b/gcc/testsuite/gcc.target/i386/long-double-80-6.c new file mode 100644 index 0000000..a395a26 --- /dev/null +++ b/gcc/testsuite/gcc.target/i386/long-double-80-6.c @@ -0,0 +1,11 @@ +/* { dg-do run } */ +/* { dg-options "-O0 -mlong-double-64 -mfpmath=387" } */ + +int +main () +{ + __float80 a = -0.23456789; + if ((double) a >= 0) + __builtin_abort (); + return 0; +} diff --git a/gcc/testsuite/gcc.target/i386/long-double-80-7.c b/gcc/testsuite/gcc.target/i386/long-double-80-7.c new file mode 100644 index 0000000..9b30fe8 --- /dev/null +++ b/gcc/testsuite/gcc.target/i386/long-double-80-7.c @@ -0,0 +1,13 @@ +/* { dg-do run } */ +/* { dg-options "-O0 -mlong-double-64 -mfpmath=sse" } */ +/* { dg-require-effective-target sse2 } */ + +#include "sse2-check.h" + +static void +sse2_test (void) +{ + __float80 a = -0.23456789; + if ((double) a >= 0) + __builtin_abort (); +} diff --git a/libgcc/config/i386/t-linux b/libgcc/config/i386/t-linux index 29b4c22..4f47f7b 100644 --- a/libgcc/config/i386/t-linux +++ b/libgcc/config/i386/t-linux @@ -2,3 +2,5 @@ # Need to support TImode for x86. Override the settings from # t-slibgcc-elf-ver and t-linux SHLIB_MAPFILES = libgcc-std.ver $(srcdir)/config/i386/libgcc-glibc.ver + +HOST_LIBGCC2_CFLAGS += -mlong-double-80